SOAP چیست؟ IBM SOAP4J چطور؟

SOAP چیست؟ IBM SOAP4J چطور؟

برت مک لافلین ترجمه ایلیا چکمنف

SOAP پروتکل دسترسی به اشیاء ساده است. اگر قبلاً چیزی در مورد آن نشنیده اید، پس باید در میانه ناکجاآباد و به دور از تمدن زندگی کنید. این به جدیدترین مد در برنامه نویسی وب و بخشی جدایی ناپذیر از خدمات وب تبدیل شده است که با چنین تعصبی در توسعه های وب جدیدترین نسل استفاده می شود. اگر نام دات نت مایکروسافت یا "انقلاب" نظیر به نظیر را شنیده اید، پس در مورد فناوری هایی شنیده اید که به SOAP متکی هستند (حتی اگر ندانید چیست). یکی نیست، اما دواجرای SOAP از آپاچی و مایکروسافت، که هزاران صفحه به آنها در سایت پشتیبانی MSDN (http://msdn.microsoft.com/) اختصاص داده شده است.

در این مقاله به شما خواهم گفت که SOAP چیست و چرا بخش مهمی در توسعه پارادایم برنامه نویسی وب است. این به شما کمک می کند که اصول اولیه را رها کنید و مستقیماً با جعبه ابزار SOAP کار کنید. سپس یک نمای کلی از پروژه‌های موجود SOAP ارائه می‌دهم و به پیاده‌سازی آپاچی می‌پردازم. این مقاله قصد ندارد تصویر کاملی از SOAP ارائه دهد. پاسخ بسیاری از سوالاتی که پس از مطالعه این مقاله مطرح شده است را در کتاب خواهید یافت.

معرفی

ابتدا باید بفهمید SOAP چیست. می‌توانید نظر کامل (و کاملاً طولانی) W3C را در http://www.w3.org/TR/SOAP بخوانید. سپس، با فهمیدن و دور انداختن تمام پوسته، متوجه خواهید شد که SOAP فقط یک پروتکل است. این یک پروتکل ساده است (نیازی به نوشتن پروتکل جدیدی برای استفاده از آن نیست) بر اساس این ایده که در یک نقطه از معماری توزیع شده نیاز به تبادل اطلاعات وجود دارد. علاوه بر این، برای سیستم هایی که در آنها امکان اضافه بار و مشکلات در فرآیندهای پردازش وجود دارد، این پروتکل بسیار سودمند است زیرا سبک وزن است و به حداقل منابع نیاز دارد. در نهایت، این اجازه می دهد تا تمام عملیات ها از طریق HTTP انجام شوند، که این امکان را فراهم می کند تا از چیزهای پیچیده ای مانند فایروال ها عبور کرده و از گوش دادن با استفاده از سوکت ها در تعداد باورنکردنی پورت محافظت کنید. نکته اصلی این است که شما این را متوجه شوید و همه چیز جزئی است.

البته شما دوست دارید این جزئیات را بدانید و من از آنها چشم پوشی نمی کنم. سه جزء اساسی برای مشخصات SOAP وجود دارد: یک پاکت SOAP، مجموعه ای از قوانین رمزگذاری، و وسیله ای برای تعامل بین درخواست و پاسخ. بیایید پیام SOAP را به عنوان یک نامه معمولی در نظر بگیریم. آیا هنوز آن چیزهای باستانی را در پاکت هایی با یک تمبر پستی و آدرسی که روی آن نوشته شده بود به یاد دارید؟ این تشبیه به شما کمک می کند مفهوم SOAP را به عنوان یک "پاکت" با وضوح بیشتری درک کنید. شکل 12-1 فرآیندهای SOAP را در قالب این قیاس نشان می دهد.

شکل 12-1. فرآیند پیام SOAP

این تصویر را در ذهن داشته باشید و به سه جزء مشخصات SOAP نگاهی بیندازیم. من به طور خلاصه در مورد هر یک از آنها صحبت می کنم و مثال هایی را ارائه می دهم که به بهترین شکل مفهوم را نشان می دهد. این سه جزء کلیدی SOAP را بسیار مهم و معنادار می کند. مدیریت خطا، پشتیبانی از رمزگذاری‌های مختلف، سریال‌سازی پارامترها و این واقعیت که SOAP بر روی HTTP کار می‌کند در بیشتر موارد آن را نسبت به راه‌حل‌های دیگر برای پروتکل‌های توزیع شده جذاب‌تر می‌کند. SOAP درجه بالایی از قابلیت همکاری با سایر برنامه‌ها را فراهم می‌کند که در کتابم با جزئیات بیشتری به آن پرداختم. در حال حاضر، من می خواهم بر روی عناصر اصلی SOAP تمرکز کنم.

پاكت نامه

پاکت SOAP شبیه به یک پاکت نامه معمولی است. این شامل اطلاعاتی در مورد پیام است که در بخش SOAP اصلی رمزگذاری می شود، از جمله اطلاعات مربوط به گیرنده و فرستنده، و همچنین اطلاعات مربوط به خود پیام. به عنوان مثال، هدر پاکت SOAP ممکن است نشان دهد که چگونه پیام باید پردازش شود. قبل از اینکه یک برنامه شروع به پردازش یک پیام کند، اطلاعات مربوط به پیام را بررسی می کند، از جمله اینکه آیا اصلاً می تواند پیام را پردازش کند یا خیر. برخلاف وضعیت تماس‌های استاندارد XML-RPC (به یاد داشته باشید؟ پیام‌های XML-RPC، رمزگذاری، و غیره، همه چیز در یک قطعه XML ترکیب می‌شود)، با SOAP پردازش مداوم به منظور یادگیری چیزی در مورد پیام اتفاق می‌افتد. یک پیام معمولی SOAP همچنین ممکن است شامل یک سبک رمزگذاری باشد که به گیرنده در پردازش پیام کمک می کند. مثال 12-1 یک پاکت SOAP را نشان می دهد که با یک مشخصات رمزگذاری به پایان می رسد.

مثال 12-1: پاکت صابون

جعبه صابون http://www-106.ibm.com/developerworks/library/x-soapbx1.html

همانطور که می بینید، رمزگذاری در داخل پاکت تنظیم شده است، که به برنامه اجازه می دهد تا (با استفاده از مقدار مشخصه) تعیین کند encodingStyle، آیا می تواند پیام دریافتی واقع در عنصر را بخواند یا خیر بدن. مطمئن شوید که فضای نام پاکت SOAP صحیح است، یا سرورهای SOAP که پیام شما را دریافت می‌کنند، خطای عدم تطابق نسخه را گزارش می‌کنند و شما نمی‌توانید با آنها ارتباط برقرار کنید.

رمزگذاری

دومین عنصر مهم SOAP امکان رمزگذاری انواع داده های سفارشی است. با RPC (و XML-RPC)، رمزگذاری فقط روی انواع داده های از پیش تعریف شده که در جعبه ابزار XML-RPC که دانلود کرده اید پشتیبانی می شوند، قابل انجام است. رمزگذاری انواع دیگر داده ها مستلزم آن است که خودتان سرور RPC و کلاینت را تغییر دهید. با SOAP، یک طرحواره XML می تواند به راحتی برای تعیین انواع داده های جدید (با استفاده از ساختار) استفاده شود. نوع پیچیده، در فصل 2 کتاب من مورد بحث قرار گرفت)، و این انواع جدید را می توان در XML به عنوان بخشی از بخش اصلی SOAP نشان داد. به لطف یکپارچه سازی طرحواره XML، می توانید هر نوع داده ای را در یک پیام SOAP با توصیف منطقی آن در یک طرحواره XML رمزگذاری کنید.

زنگ زدن

بهترین راه برای درک نحوه عملکرد تماس SOAP مقایسه آن با چیزی است که با آن آشنا هستید، مانند XML-RPC. اگر به خاطر داشته باشید، فراخوانی XML-RPC شبیه به قطعه کد ارائه شده در مثال 12-2 به نظر می رسد.

مثال 12-2. با XML-RPC تماس بگیرید

// تعیین پردازنده XML (تجزیه کننده) برای استفاده از XmlRpc.setDriver("org.apache.xerces.parsers.SAXParser"); // تعیین سروری که اتصال به آن برقرار می شود XmlRpcClient Client = new XmlRpcClient("http://rpc.middleearth.com"); // ایجاد پارامترهای Vector params = new Vector(); params.addElement(flightNumber); params.addElement(numSeats); params.addElement(creditCardType); params.addElement(creditCardNum); // درخواست Boolean buyTickets = (Boolean)client.execute("ticketCounter.buyTickets", params); // پاسخ را پردازش کنید

من یک برنامه ساده برای سفارش بلیط هواپیما ایجاد کردم. اکنون به مثال 12-3 نگاهی بیندازید که یک تماس SOAP را نشان می دهد.

مثال 12-3. تماس با SOAP

// ایجاد پارامترهای Vector params = new Vector(); params.addElement(new Parameter("flightNumber"، Integer.class، flightNumber، null)); params.addElement(پارامتر جدید ("numSeats"، Integer.class، numSeats، null)); params.addElement (پارامتر جدید ("creditCardType"، String.class، creditCardType، null)); params.addElement(پارامتر جدید ("creditCardNumber"، Long.class، creditCardNum، null)); // ایجاد یک شیء Call Call call = new Call(); call.setTargetObjectURI("urn:xmltoday-airline-tickets"); call.setMethodName("buyTickets"); call.setEncodingStyleURI(Constants.NS_URI_SOAP_ENC); call.setParams(params); // Call Response res = call.invoke(new URL("http://rpc.middleearth.com")، ""); // پاسخ را پردازش کنید

همانطور که می بینید، تماس واقعی توسط شی نشان داده می شود زنگ زدن، ساکن حافظه. این به شما امکان می دهد هدف تماس، روش تماس، سبک رمزگذاری، پارامترها و بسیاری از پارامترهای دیگر که در این مثال ارائه نشده اند را مشخص کنید. این مکانیزم انعطاف‌پذیرتر از روش XML-RPC است که به شما امکان می‌دهد مجموعه‌ای از پارامترهای مختلف را که به طور ضمنی در XML-RPC تعریف شده‌اند، به‌صراحت مشخص کنید. در ادامه این مقاله، درباره فرآیند تماس، از جمله نحوه رسیدگی به درخواست‌های نامعتبر توسط SOAP، سلسله مراتب خطا، و البته نتایج تماس برگشتی، اطلاعات بیشتری کسب خواهید کرد.

پس از چنین مقدمه ای کوتاه، از قبل به اندازه کافی می دانید که به این موضوع خنده دار علاقه مند شوید. حالا اجازه دهید شما را با اجرای SOAP که قرار است از آن استفاده کنم، معرفی کنم. من دلایل انتخاب آن را توضیح خواهم داد و به چند نمونه کد نگاه می کنم.

تنظیمات

اکنون که اصول اولیه این مفهوم را یاد گرفتید، نوبت به بخش سرگرم کننده آن رسیده است: برنامه نویسی. برای انجام این کار، به یک پروژه یا محصول مناسب نیاز دارید، که پیدا کردن آن آسان تر از آن چیزی است که در نگاه اول به نظر می رسد. اگر به یک پروژه جاوا نیاز دارید که قابلیت‌های SOAP را ارائه می‌کند، لازم نیست مدت زیادی برای یافتن آن جستجو کنید. دو گروه از محصولات وجود دارد: تجاری و رایگان. همانطور که در کتابم است، از ذکر محصولات تجاری خودداری می کنم. این اصلاً به این دلیل نیست که آنها بد هستند (برعکس، برخی از آنها عالی هستند)، بلکه به این دلیل است که من دوست دارم هر خواننده بتواند هر یک از مثال های ارائه شده را امتحان کند. این به دلیل دسترسی است که بسیاری از محصولات تجاری از آن بی بهره هستند. برای استفاده از آنها باید هزینه پرداخت کنید یا به طور موقت پس از دانلود برای مدت محدودی از آنها استفاده کنید.

بنابراین، ما به آرامی به پروژه های منبع باز نزدیک شدیم. از این منطقه فقط می توانم یک محصول را نام ببرم: صابون آپاچی. این در http://xml.apache.org/soap قرار دارد و جعبه ابزار SOAP را برای جاوا فراهم می کند. در زمان نگارش این مطلب نسخه 2.2 منتشر شد که می توانید آن را از وب سایت آپاچی دانلود کنید. این نسخه ای است که در نمونه های این مقاله استفاده خواهم کرد.

جایگزین های دیگر

قبل از شروع به نصب و پیکربندی Apache SOAP، به چند سوالی که ممکن است در ذهن شما رخنه کرده باشد پاسخ خواهم داد. فکر می کنم دلایل استفاده نکردن از محصولات تجاری را کاملاً واضح توضیح داده ام. با این حال، ممکن است به پروژه های منبع باز یا مرتبط دیگری فکر کنید که ممکن است دوست داشته باشید از آنها استفاده کنید، و تعجب کرده اید که من در مورد آنها نظری نداده ام.

در مورد IBM SOAP4J چطور؟

اولین بار در لیست جایگزین ها، یک پیاده سازی از IBM است: SOAP4J. کار IBM اساس پروژه Apache SOAP را تشکیل داد، درست همانطور که XML4J IBM به چیزی تبدیل شد که اکنون به عنوان پروژه تجزیه کننده XML Apache Xerces شناخته می شود. فرض بر این است که پیاده سازی IBM دوباره طراحی خواهد شد و با Apache SOAP ادغام خواهد شد. تقریباً همین اتفاق در مورد XML4J IBM افتاد: اکنون فقط در Xerces بسته بندی را ارائه می دهد - تولید کنندگان بزرگ اغلب از پروژه های OpenSource پشتیبانی می کنند و از آنها استفاده می کنند، در این مورد هر دو پروژه (Apache و IBM) از یک پایه کد استفاده می کنند.

آیا مایکروسافت از بازی خارج شده است؟

البته که نه. مایکروسافت و اجرای SOAP آن، و همچنین کل جنبش دات نت (که در کتاب من با جزئیات بیشتر مورد بحث قرار گرفته است)، بسیار مهم هستند. من واقعاً می‌خواستم بیشتر وقتم را به جزئیات پیاده‌سازی SOAP مایکروسافت بپردازم، اما فقط از اشیاء COM پشتیبانی می‌کند و جاوا را پشتیبانی نمی‌کند. با توجه به این دلایل، چنین توصیفی نمی تواند در مقاله ای در مورد جاوا و XML گنجانده شود. با این حال، مایکروسافت (علیرغم همه شکایت هایی که ما به عنوان توسعه دهندگان از این شرکت داریم) کارهای مهمی در زمینه خدمات وب انجام داده است و اگر بدون فکر و تنها با هدایت احساسات خام آن را کنار بگذارید، اشتباه خواهید کرد. اگر نیاز به کار با کامپوننت‌های COM یا Visual Basic دارید، به شدت توصیه می‌کنم از جعبه ابزار Microsoft SOAP که در http://msdn.microsoft.com/library/default.asp?url=/nhp/Default موجود است استفاده کنید. .asp ?contentid=28000523 به همراه بسیاری از منابع SOAP دیگر.

اکسیس چیست؟

کسانی از شما که فعالیت های آپاچی را دنبال می کنید حتما نام Apache Axis را شنیده اید. Axis یک جعبه ابزار SOAP نسل بعدی است که تحت چتر Apache XML نیز توسعه یافته است. SOAP (یک مشخصات، نه یک پیاده سازی خاص)، که اخیراً به سرعت و به طور اساسی در حال توسعه است، بسیار دشوار است. تلاش برای ایجاد نسخه ای از SOAP که به طور کامل الزامات فعلی را مطابق با تکامل آنها برآورده کند نیز بسیار چالش برانگیز است. در نتیجه، نسخه فعلی Apache SOAP راه حلی را ارائه می دهد که با طراحی آن محدود شده است. توسعه دهندگان آپاچی با تصمیم به اینکه ارزش تلاش برای بازطراحی کامل ابزار موجود را ندارد، شروع به ایجاد پروژه ای بر اساس کد جدید کردند. بدین ترتیب اکسیس متولد شد. نام SOAP نیز ابتدا از SOAP به XP و سپس به XMLP تغییر کرد. سپس نام مشخصات از نام SOAP جدید حذف شد و نام "Axis" متولد شد. اما اکنون به نظر می رسد که W3C به نام مشخصات SOAP (نسخه 1.2 یا 2.0) برمی گردد، بنابراین ممکن است همه چیز همچنان تغییر کند و سردرگمی حتی بیشتر شود!

به IBM SOAP4J به عنوان یک معماری؟1 از جعبه ابزار SOAP فکر کنید. در مورد Apache SOAP (در این مقاله بحث شده) به عنوان یک معماری چطور؟ و Axis معماري ?3، معماري نسل جديد را نشان مي دهد. این پروژه از SAX استفاده می کند در حالی که Apache SOAP مبتنی بر DOM است. علاوه بر این، Axis، بر خلاف Apache SOAP، رویکرد کاربر پسندتری را برای تعامل با کاربر ارائه می دهد. پس از برشمردن این مزایا، شاید تعجب کنید که چرا اکسیس را به عنوان موضوع مطالعه انتخاب نکردم. فقط کمی زودرس خواهد بود. در حال حاضر تنها نسخه 0.51 اکسیس در حال آماده سازی برای انتشار است. این هنوز نسخه بتا یا حتی یک نسخه آلفا نیست. من دوست دارم در مورد ویژگی های جدید Axis صحبت کنم، اما شما شانسی برای متقاعد کردن مدیریت خود ندارید که می توانید از نرم افزار منبع باز زیر آلفا برای نیازهای حیاتی سیستم خود استفاده کنید. بنابراین تصمیم گرفتم روی چیزی تمرکز کنم که شما واقعی هستید شما می توانید استفاده کنیدقبلا، پیش از این امروز- صابون آپاچی فکر می کنم تا زمانی که نسخه نهایی Apache Axis منتشر شود، این مطالب را در نسخه بعدی کتابم به روز خواهم کرد. تا آن زمان، بیایید روی راه حلی که از قبل در دسترس است تمرکز کنیم.

نصب و راه اندازی

دو شکل ممکن برای نصب SOAP وجود دارد. اولین مورد این است که یک کلاینت SOAP را با استفاده از SOAP API برای برقراری ارتباط با سروری که می تواند پیام های SOAP را بپذیرد، راه اندازی کنید. راه دوم اجرای یک سرور SOAP است که می تواند پیام ها را از مشتری SOAP دریافت کند. در این بخش من هر دو روش را شرح داده ام.

مشتری

برای استفاده از سرویس گیرنده SOAP، ابتدا باید Apache SOAP را دانلود کنید که در http://xml.apache.org/dist/soap موجود است. من نسخه 2.2 را با فرمت باینری (از زیر شاخه دانلود کردم نسخه 2.2). سپس باید محتویات بایگانی را در فهرستی در رایانه خود از حالت فشرده خارج کنید. در مورد من دایرکتوری بود javaxml2 (c:\javaxml2در کامپیوتر ویندوز من /javaxml2در رایانه Mac OS X من). در نتیجه فایل ها از حالت فشرده خارج شدند /javaxml2/soap-2_2. همچنین باید بسته JavaMail را که از سایت Sun http://java.sun.com/products/javamail/ در دسترس است دانلود کنید. برای پشتیبانی از پروتکل انتقال SMTP مورد استفاده توسط Apache SOAP مورد نیاز است. سپس Java Beans Activation Framework (JAF) را که از Sun http://java.sun.com/products/beans/glasgow/jaf.html نیز در دسترس است، دانلود کنید. بر اساس این فرض که قبلا Xerces یا تجزیه کننده XML دیگری را نصب کرده اید و آماده استفاده هستید.

توجه داشته باشید:مطمئن شوید که تجزیه کننده XML شما با JAXP سازگار است و از فضای نام به درستی استفاده می کند. تجزیه کننده شما به احتمال زیاد این شرایط را برآورده می کند اگر مشکل دارید، بهتر است به استفاده از Xerces برگردید.

توجه داشته باشید:از آخرین نسخه های Xerces استفاده کنید. نسخه 1.4 و بالاتر این کار را انجام خواهد داد. تعدادی اشکال در SOAP و Xerces 1.3(.1) وجود دارد، بنابراین توصیه می کنم از این ترکیب استفاده نکنید.

بسته های JavaMail و JAF را از حالت فشرده خارج کنید و سپس فایل های jar آنها را در مسیر کلاس خود و همچنین کتابخانه قرار دهید. صابون.شیشه. هر یک از این فایل های jar باید یا در دایرکتوری ریشه برنامه مربوطه یا در یک زیر شاخه قرار داشته باشند /lib. وقتی متغیر شما تمام شد مسیر کلاسباید چیزی شبیه به این باشد:

$ echo $CLASSPATH /javaxml2/soap-2_2/lib/soap.jar:/javaxml2/lib/xerces.jar: /javaxml2/javamail-1.2/mail.jar:/javaxml2/jaf-1.0.1/activation.jar

برای ویندوز به شکل زیر خواهد بود:

c:\>echo %CLASSPATH% c:\javaxml2\soap-2_2\lib\soap.jar;c:\javaxml2\lib\xerces.jar; c:\javaxml2\javamail-1.2\mail.jar;c:\javaxml2\jaf-1.0.1\activation.jar

و در نهایت دایرکتوری را اضافه کنید javaxml2/soap-2_2/در شما مسیر کلاسبرای اجرای نمونه های SOAP. من تنظیمات را برای چندین مثال در این فصل شرح داده ام.

سرور

برای ایجاد مجموعه ای از اجزای سرور سازگار با SOAP، ابتدا به یک موتور سرولت نیاز دارید. مانند فصل های قبلی، من از آپاچی تامکت (موجود در http://jakarta.apache.org/) به عنوان مثال برای این فصل استفاده کردم. شما باید هر آنچه مشتری نیاز دارد را به آن اضافه کنید مسیر کلاسسرور ساده ترین راه برای انجام این کار، تنظیم مجدد است صابون.شیشه, activation.jarو mail.jarو همچنین تجزیه کننده شما، به دایرکتوری کتابخانه های موتور سرولت شما. برای Tomcat، این دایرکتوری /lib است که شامل کتابخانه هایی برای بارگیری خودکار است. اگر می‌خواهید از اسکریپت‌ها پشتیبانی کنید (که در این فصل مورد بحث قرار نگرفته‌اند، اما در نمونه‌های Apache SOAP هستند)، باید قرار دهید bsf.jar(موجود در http://oss.software.ibm.com/developerworks/projects/bsf) و js.jar(موجود در http://www.mozilla.org/rhino/) به همان دایرکتوری.

توجه داشته باشید:اگر از Xerces با Tomcat استفاده می کنید، باید ترفندی را که در فصل 10 توضیح دادم تکرار کنید. تغییر نام تجزیه کننده.جار V z_parser.jar، آ jaxp.jar V z_jaxp.jarبرای اطمینان از آن xerces.jarو نسخه گنجانده شده JAXP قبل از هر تجزیه کننده یا پیاده سازی JAXP دیگر بارگذاری می شود.

سپس موتور servlet خود را مجدداً راه اندازی کنید، پس از آن آماده نوشتن اجزای سرور SOAP هستید.

Router Servlet و Admin Client

جدا از عملیات اصلی، Apache SOAP شامل یک سرور روتر و همچنین یک سرویس گیرنده مدیریت است. حتی اگر قصد استفاده از آنها را ندارید، توصیه می کنم آنها را نصب کنید تا آزمایش کنید که SOAP به درستی نصب شده است. این فرآیند بستگی به این دارد که شما از کدام موتور servlet استفاده می کنید، بنابراین من روند نصب را به Tomcat محدود می کنم. دستورالعمل‌های نصب برای برخی دیگر از موتورهای سرولت را می‌توانید در http://xml.apache.org/soap/docs/index.html بیابید.

نصب تحت Tomcat بسیار ساده است: فقط فایل را بگیرید صابون.جنگاز دایرکتوری soap-2_2/webappsو آن را در دایرکتوری قرار دهید $TOMCAT_HOME/برنامه های وب- و بس! برای بررسی نصب، آدرس را در مرورگر خود وارد کنید http://localhost:8080/soap/servlet/rpcrouter. شما باید پاسخی مشابه آنچه در شکل 12-2 نشان داده شده است دریافت کنید.

شکل 12-2. روتر RPC Servlet

اگرچه به نظر می رسد پیام یک پیام خطا است، اما نشان می دهد که همه چیز به درستی کار می کند. اگر مرورگر خود را به آدرس مشتری مدیر اشاره کنید، باید همان پاسخ را دریافت کنید: http://localhost:8080/soap/servlet/messagerouter.

برای اتمام تست سرور و کلاینت، مطمئن شوید که تمام دستورالعمل ها را به طور کامل دنبال کرده اید. سپس کلاس جاوا زیر را مطابق شکل زیر اجرا کنید تا از URL سرولت خود برای سرورلت روتر RPC پشتیبانی کند:

C:\>java org.apache.soap.server.ServiceManagerClient http://localhost:8080/soap/servlet/rpcrouter list خدمات مستقر شده:

همانطور که در بالا نشان داده شده است باید یک لیست خالی از خدمات دریافت کنید. اگر پیامی دریافت کردید، لطفاً لیست طولانی خطاهای احتمالی موجود در http://xml.apache.org/soap/docs/trouble/index.html را مرور کنید. این فهرست جامع ترین مشکلاتی است که ممکن است با آن مواجه شوید. اگر یک لیست خالی دریافت کردید، به این معنی است که راه اندازی کامل شده است و شما آماده هستید تا نمونه های ارائه شده در این فصل را مشاهده کنید.

بیا شروع کنیم

سه مرحله اصلی برای نوشتن هر سیستم مبتنی بر SOAP وجود دارد. پس از فهرست کردن آنها، به طور خلاصه به هر یک از آنها می پردازم:

  • انتخاب بین پیام های SOAP-RPC و SOAP.
  • نوشتن یا دسترسی به یک سرویس SOAP؛
  • نوشتن یا دسترسی به مشتری SOAP.

اولین قدم این است که انتخاب کنید آیا از SOAP برای تماس‌های RPC (که در آن یک رویه از راه دور بر روی سرور اجرا می‌شود) یا پیام‌ها (که در آن مشتری به سادگی بخش‌هایی از اطلاعات را به سرور ارسال می‌کند) استفاده کنید. در زیر به تفصیل درباره این فرآیندها صحبت می کنم. هنگامی که این تصمیم را گرفتید، باید به سرویس خود دسترسی داشته باشید یا آن را ایجاد کنید. البته، از آنجایی که همه ما حرفه ای جاوا هستیم، این فصل به نحوه ایجاد جاوا می پردازد. و در نهایت، شما باید یک مشتری برای این سرویس بنویسید، تمام!

RPC یا پیام رسانی؟

اولین کار شما ربطی به برنامه نویسی ندارد و بیشتر جنبه طراحی دارد. باید انتخاب کنید که از سرویس RPC یا پیام‌ها استفاده کنید. فرض می کنیم که شما با RPC آشنایی دارید (مثلاً با خواندن یکی از فصل های کتاب من). کلاینت یک رویه از راه دور را روی سرور اجرا می کند و سپس یک پاسخ دریافت می کند. در این سناریو، SOAP به عنوان یک سیستم پیشرفته XML-RPC عمل می کند که مدیریت بهتر خطا و انتقال انواع داده های پیچیده را از طریق شبکه فراهم می کند. شما قبلاً با این مفهوم آشنا هستید و از آنجایی که نوشتن سیستم های RPC در SOAP آسان تر است، من با آنها شروع می کنم. این مقاله نحوه ایجاد یک سرویس RPC، یک کلاینت RPC و اجرای سیستم را شرح می دهد.

روش دیگر کار SOAP مبتنی بر تبادل پیام است. به جای انجام مراحل از راه دور، فقط برای تبادل اطلاعات استفاده می شود. همانطور که می توانید حدس بزنید، این یک ابزار قدرتمند است که نیازی به اطلاع مشتری از روش های جداگانه هیچ سروری ندارد. همچنین با اجازه دادن به بسته‌های داده (بسته‌ها به معنای مجازی، نه به معنای شبکه) برای ارسال به سیستم‌های دیگر، مدل‌سازی سیستم‌های راه دور را بیشتر ایزوله می‌کند. در عین حال، سیستم های دیگر نیازی به اطلاع از عملیاتی که با این داده ها انجام شده است ندارند. این سبک پیچیده تر از برنامه نویسی RPC است، بنابراین من آن را در اینجا شرح نمی دهم. شما آن را در کتاب من به همراه سایر جزئیات تعامل بین کسب و کار خواهید یافت. ابتدا با برنامه نویسی SOAP-RPC آشنا شوید.

مانند بسیاری از مشکلات طراحی، تصمیم گیری به عهده شماست. برنامه خود را تجزیه و تحلیل کنید و سعی کنید مشخص کنید که چرا باید از SOAP استفاده کنید. اگر یک سرور و مجموعه ای از مشتریان دارید که عملکردهای تجاری خاصی را بر اساس تقاضا انجام می دهند، RPC برای شما مناسب تر است. در سیستم‌های پیچیده‌ای که در آن تبادل داده‌ها چیزی بیش از انجام وظایف تجاری خاص در صورت تقاضا است، استفاده از پیام‌های SOAP بسیار ترجیح داده می‌شود.

سرویس RPC

اکنون که تشریفات به پایان رسیده است، زمان اقدام فرا رسیده است. همانطور که می دانید در RPC به کلاس هایی نیاز دارید که متدهای آنها از راه دور اجرا شود.

قطعه کد

من با نگاه کردن به چند قطعه کد برای سرور شروع می کنم. این قطعات کلاس هایی با متدهایی هستند که برای کلاینت های RPC اجرا می شوند. من از کد کتابم به عنوان مثال استفاده کردم. به جای استفاده از کلاس‌های ساده، مثال پیچیده‌تری را انتخاب کردم تا قابلیت‌های SOAP را تا حد امکان به وضوح نشان دهم. بنابراین، من از کلاس CD به عنوان مثال استفاده کردم. ابتدا عنصر را تعریف می کنیم نقشهبرای هر نوع پارامتر غیر استاندارد برای صفت encodingStyleحداقل در Apache SOAP 2.2. شما باید مقدار http://schemas.xmlsoap.org/soap/encoding/ را مشخص کنید. این در حال حاضر تنها رمزگذاری پشتیبانی شده است. شما باید فضای نام را برای نوع تعریف شده توسط کاربر و سپس نام کلاس را با فضای نام برای آن نوع مشخص کنید. در مورد ما، برای این اهداف از یک فضای نام ساختگی و یک پیشوند ساده استفاده کردم. ایکسسپس با استفاده از ویژگی جاوا تایپ، نام واقعی کلاس جاوا را تنظیم کنید (برای این مورد - javaxml2.CD). و بالاخره کورالسیل با صفات java2XMLClassNameو xml2JavaClassName. با کمک آنها کلاسی مشخص می شود که از جاوا به XML و بالعکس تبدیل می شود. من از کلاس بسیار مفید BeanSerializer استفاده کردم که همراه با Apache SOAP نیز موجود است. اگر پارامتر سفارشی شما در قالب JavaBean باشد، این سریال‌ساز و deserializer شما را از نوشتن مطالب خود نجات می‌دهد. شما به یک کلاس با سازنده پیش فرض نیاز دارید (به یاد داشته باشید، برای کلاس CD یک سازنده ساده و بدون پارامتر تعریف کردم)، و تمام داده های این کلاس را با استفاده از روش ها منتشر کنید. مجموعهXXXو دریافتXXX. چون کلاس سی دیکاملاً تمام این الزامات را برآورده می کند، BeanSerializerعالی کار می کند

توجه داشته باشید:چه کلاسی سی دیالزامات را برآورده می کند BeanSerializer. زیاد مهم نیست اکثر کلاس ها به راحتی به این فرمت تبدیل می شوند. بنابراین توصیه می‌کنم از نوشتن سریال‌سازها و سریال‌سازهای خودتان اجتناب کنید. این یک سردرد اضافی است (هیچ چیز پیچیده ای نیست، اما بسیار پر زحمت است) و من توصیه می کنم در انرژی خود صرفه جویی کنید و از تبدیل لوبیا در پارامترهای سفارشی خود استفاده کنید. در بسیاری از موارد، تبدیل bean فقط به یک سازنده پیش‌فرض (بدون پارامتر) در کلاس شما نیاز دارد.

حالا بیایید دوباره بسازیم شیشهسرویس ما را فایل و دوباره نصب کنید:

(gandalf)/javaxml2/Ch12$ جاوا org.apache.soap.server.ServiceManagerClient http://localhost:8080/soap/servlet/rpcrouter xml/CDCatalogDD.xml

توجه:اگر موتور servlet خود را روشن بگذارید و یک سرویس را مجدداً میزبانی کنید، باید موتور servlet را مجدداً راه اندازی کنید تا کلاس های جدید برای سرویس SOAP فعال شود و سرویس مجدداً میزبانی شود.

اکنون تنها چیزی که باقی می ماند تغییر کلاینت برای استفاده از کلاس ها و متدهای جدید است. مثال 12-10 شامل یک نسخه اصلاح شده از کلاس مشتری است CDAdder. تغییرات ایجاد شده در نسخه قبلی برجسته شده است.

مثال 12-10: کلاس CDAdder به روز شده

بسته javaxml2; وارد کردن java.net.URL; واردات java.util.Vector; واردات org.apache.soap.Constants; وارد کردن org.apache.soap.Fault; واردات org.apache.soap.SOAPxception; وارد کردن org.apache.soap.encoding.SOAPMappingRegistry. واردات org.apache.soap.encoding.soapenc.BeanSerializer.واردات org.apache.soap.rpc.Call; واردات org.apache.soap.rpc.Parameter; واردات org.apache.soap.rpc.Response; وارد کردن org.apache.soap.util.xml.QName; کلاس عمومی CDAdder( افزودن خالی عمومی (URL URL، عنوان رشته، هنرمند رشته، برچسب رشته) SOAPException ( System.out.println("افزودن سی دی با عنوان "" + عنوان + "" هنرمند "" + هنرمند + "" استودیو " + برچسب); سی دی سی دی = سی دی جدید (عنوان، هنرمند، برچسب)؛ // ایجاد یک شیء فراخوانی Call Call call = new Call(); call.setSOAPMappingRegistry(رجیستری); call.setTargetObjectURI("urn:cd-catalog"); call.setMethodName("addCD"); call.setEncodingStyleURI(Constants.NS_URI_SOAP_ENC); // تنظیم پارامترها Vector params = new Vector(); params.addElement(new Parameter("cd", CD.class, cd, null)); call.setParams(params); // پردازش پاسخ فراخوانی پاسخ. answer = call.invoke(url, ""); if (!response.generatedFault()) ( System.out.println ("افزودن سی دی با موفقیت انجام شد.")؛ else ( خطا = answer.getFault()؛ System.out.println (خطا: " + fault.getFaultString ())؛ public static void main(string args) ( if (args.length != 4) ( System.out.println("Template: java javaxml2.CDAdder " + "\"[CD Title]\" \"[Artist Name]\ " \"[سی دی استودیو]\""); سعی کنید (// URL سرور SOAP که اتصال به آن برقرار شده است URL URL = URL new(args); // دریافت مقادیر برای عنوان رشته CD جدید = args; هنرمند رشته = ارگ; برچسب رشته = args; // افزودن CD CDAdder = new CDAdder(); adder.add(url، عنوان، هنرمند، برچسب)؛ ) catch (Exception e) (e.printStackTrace(); ) ) )

تنها تغییر واقعا جالب در نقشه برداری کلاس است سی دی:

// این نوع را نقشه برداری کنید تا بتوان با SOAP SOAPMappingRegistry Registry = new SOAPMappingRegistry(); BeanSerializer serializer = new BeanSerializer(); registry.mapTypes(Constants.NS_URI_SOAP_ENC، QName جدید ("urn:cd-catalog-demo"، "cd")، CD.class، serializer، serializer);

به این ترتیب می توان یک پارامتر کاربر را رمزگذاری کرد و از طریق شبکه منتقل کرد. من قبلا به شما گفته ام که چگونه کلاس BeanSerializerمی تواند برای پردازش پارامترها در قالب JavaBean مانند کلاس استفاده شود سی دی. من از یک توصیفگر مکان برای نشان دادن این موارد به سرور استفاده کردم، اگرچه اکنون باید به کلاینت بگویم که از این سریال ساز و deserializer استفاده کند. این تابع توسط کلاس انجام می شود SOAPMappingRegistry. روش mapTypes()رشته رمزگذاری شده را می گیرد (باز هم بهتر است از یک ثابت برای این کار استفاده کنید NS_URI_SOAP_ENC) و اطلاعات مربوط به نوع پارامتری که باید از سریال سازی ویژه برای آن استفاده شود. ابتدا QName مشخص شده است. به همین دلیل است که از فضای نام عجیب در توصیفگر میزبانی استفاده شده است. شما باید همان URN را در اینجا و همچنین نام محلی عنصر (برای مثال "CD") و سپس شی جاوا را ارائه کنید. کلاسکلاسی که سریالی می شود ( CD.class) و در نهایت یک نمونه از کلاس برای سریال سازی و سریال زدایی. برای این مثال، هر دو مورد شامل یک نمونه خواهد بود BeanSerializer. پس از وارد شدن تمام این تنظیمات به رجیستری، شی را مطلع کنید زنگ زدنبا استفاده از روش setSOAPMapping-Registry().

می توانید این کلاس را همانطور که قبلا نشان داده شده اجرا کنید، یک سی دی اضافه کنید، و همه چیز باید همانطور که انتظار می رود کار کند:

C:\javaxml2\build>java javaxml2.CDAdder http://localhost:8080/soap/servlet/rpcrouter "Tony Rice" "Manzanita" "Sugar Hill"افزودن یک سی دی با عنوان "تونی رایس" توسط Sugar Hill's "Manzanita" با موفقیت یک سی دی اضافه شد.

من اصلاح کلاس را ترک کردم CDListerبرای شما. همه چیز طبق همان قالب تولید می شود. برای محک زدن خود می توانید به فایل های نمونه کتاب من که قبلاً شامل این کلاس های به روز شده است مراجعه کنید.

توجه: شما می توانید تصمیم بگیرید که به دلیل کلاس CDListerبه طور مستقیم با شی تعامل ندارد سی دی(با روش برگردانده شد لیست ()نوع مهم است قابل هشت)، پس نیازی به ایجاد هیچ تغییری ندارید. با این حال، کلاس بازگشت قابل هشتشامل نمونه های شی سی دی. اگر SOAP نداند که چگونه آنها را deserialize کند، مشتری خطا خواهد کرد. در این صورت برای حل مشکل باید در شی مشخص کنید زنگ زدنکپی 🀄 SOAPMappingRegistry.

مدیریت خطا کارآمد

اکنون که اشیاء سفارشی را دیدید و تماس‌های RPC و مواردی از این دست برقرار کردید، اجازه دهید در مورد موضوع کمتر هیجان‌انگیزی صحبت کنم: مدیریت خطا. با هر تراکنش شبکه، خرابی های زیادی ممکن است رخ دهد. سرویس شروع نمی شود، یک خطا در سرور وجود دارد، یک شی پیدا نمی شود، کلاس ها از بین رفته اند و بسیاری از مشکلات دیگر. تا اینجا من به سادگی از روش استفاده کردم fault.getString()برای ایجاد پیام های خطا اما این روش ممکن است همیشه مفید نباشد. برای اینکه آن را در عمل ببینید، سازنده را از نظر خارج کنید CDCatalog:

عمومی CDCatalog() ( //catalog = new Hashtable(); // ایجاد یک دایرکتوری addCD(CD جدید ("Nickel Creek", "Nickel Creek", "Sugar Hill")); addCD(CD جدید ("بگذارید سقوط کند"، "شان واتکینز"، "Sugar Hill")); addCD(CD جدید ("مرزهای هوایی"، "مایکل هجز"، "ویندهام هیل")); addCD(CD جدید ("Taproot"، "Michael Hedges"، "Windham Hill")); )

آن را دوباره کامپایل کنید، موتور servlet را مجددا راه اندازی کنید و آن را مجدداً میزبانی کنید. این منجر به یک استثنا خواهد شد NullPointerExceptionهنگامی که سازنده کلاس سعی می کند CD را به uninitialized اضافه کند قابل هشت. هنگام راه اندازی مشتری، یک پیام خطا ظاهر می شود، اما بسیار آموزنده نخواهد بود:

(gandalf)/javaxml2/build$ java javaxml2.CDLister http://localhost:8080/soap/servlet/rpcrouter فهرست سی دی فعلی را مشاهده کنید. خطا: قادر به حل موضوع هدف نیست: null

این اصلاً اطلاعاتی نیست که بتواند به شناسایی و تصحیح یک خطا کمک کند. با این وجود، چارچوب به خوبی با مدیریت خطا مقابله می کند. یادت میاد DOMFaultListener، که شما به عنوان مقدار عنصر مشخص کرده اید faultListener? زمان ورود او به بازی فرا رسیده است. شیء در صورت خطا برگردانده می شود عیبحاوی DOM (مدل شیء سند) org.w3c.dom.Elementبا اطلاعات دقیق در مورد خطا. ابتدا یک عبارت import را به کد منبع خود اضافه کنید java.util.Iterator:

وارد کردن java.net.URL; وارد کردن java.util.Enumeration; واردات java.util.Hashtable; وارد کردن java.util.Iterator;واردات java.util.Vector; واردات org.apache.soap.Constants; وارد کردن org.apache.soap.Fault; واردات org.apache.soap.SOAPexception; وارد کردن org.apache.soap.encoding.SOAPMappingRegistry. واردات org.apache.soap.encoding.soapenc.BeanSerializer. واردات org.apache.soap.rpc.Call; واردات org.apache.soap.rpc.Parameter; واردات org.apache.soap.rpc.Response; وارد کردن org.apache.soap.util.xml.QName;

حال اجازه دهید تغییراتی را برای رسیدگی به خطاها در متد list() ایجاد کنیم:

if (!response.generatedFault()) ( پارامتر returnValue = answer.getReturnValue()؛ کاتالوگ Hashtable = (Hashtable)returnValue.getValue(); Enumeration e = catalog.keys(); while (e.hasMoreElements()) ( رشته title = (String)e.nextElement(); + " studios " + cd.getLabel() ) else ( Fault fault = response.getFault(); System.out.println("Error:" +fault.getFaultString()); ورودی های برداری = fault.getDetailEntries(); برای (Iterator i = entries.iterator(); i.hasNext();) ( org.w3c.dom.Element ورودی = (org.w3c.dom.Element)i.next(); System.out.println(entry .getFirstChild().getNodeValue());

با استفاده از روش getDetailEntries()شما به سرویس SOAP و سروری که از داده های خام پشتیبانی می کند با اطلاعات مربوط به مشکل دسترسی پیدا می کنید. کد آنها را دوباره پردازش می کند (معمولا فقط یک عنصر وجود دارد، اما نیاز به توجه دقیق دارد) و DOM را رهگیری می کند. عنصر، در هر ورودی موجود است. در اصل، XML شما با آن کار می کنید:

SOAP-ENV:Server.BadTargetObjectURI نمی توان هدف را حل کرد: null این چیزی است که میخواهیم!

به عبارت دیگر، شی Fault به شما امکان دسترسی به بخشی از پاکت SOAP را می دهد که حاوی خطا است. علاوه بر این، Apache SOAP یک ردیابی پشته جاوا را هنگام رخ دادن خطا ارائه می دهد و اطلاعات دقیق مورد نیاز برای اصلاح آنها را ارائه می دهد. رهگیری یک عنصر stackTraceو چاپ مقدار گره متناز این عنصر مشتری شما می تواند ردیابی پشته سرور را چاپ کند. با کامپایل کردن این تغییرات و راه اندازی مجدد مشتری، نتیجه زیر را دریافت خواهید کرد:

C:\javaxml2\build>java javaxml2.CDLister http://localhost:8080/soap/servlet/rpcr outer فهرست سی دی فعلی را مشاهده کنید. خطا: نمی توان target: null java.lang.NullPointerException را در javaxml2.CDCatalog.addCD(CDCatalog.java:24) در javaxml2.CDCatalog حل کرد. (CDCatalog.java:14) در java.lang.Class.newInstance0 (روش بومی) در java.lang.Class.newInstance (Class.java:237)

این خیلی بهتر نیست، اما حداقل می توانید برخی از اطلاعات را ببینید که یک استثنا رخ داده است NullPointerExceptionو حتی شماره خطوط را در کلاس های سروری که این مشکل در آنها رخ داده است، بیابید. نتیجه این آخرین تغییرات تصویر واضحی از مشکل رسیدگی به خطا به شما داده است. اکنون باید کلاس های سرور خود را از نظر خطا بررسی کنید. بله، تقریباً فراموش کردم، قبل از آن فراموش نکنید که کلاس خود را دوباره تغییر دهید CDCatalogبرای خلاص شدن از شر خطاهایی که عمداً برای وضوح معرفی کردیم!

  1. صحبت های زیادی در مورد اجرای SOAP بر روی پروتکل های دیگر مانند SMTP (یا حتی Jabber) وجود دارد. استاندارد SOAP هنوز این مورد را ارائه نکرده است، اما ممکن است در آینده قابلیت های مشابهی اضافه شود. بنابراین، اگر با بحث های فعال در مورد این موضوع مواجه شدید، تعجب نکنید.
  • آموزش

سلام به همه!
این اتفاق افتاد که اخیراً شروع به توسعه خدمات وب کردم. اما امروز موضوع در مورد من نیست، بلکه در مورد این است که چگونه می توانیم وب سرویس XML خود را بر اساس پروتکل SOAP 1.2 بنویسیم.

امیدوارم پس از مطالعه موضوع بتوانید:

  • پیاده سازی سرور خود را از یک برنامه وب بنویسید.
  • پیاده سازی یک برنامه وب با مشتری خود را بنویسید.
  • شرح خدمات وب خود را بنویسید (WSDL).
  • آرایه های مشتری از همان نوع داده را به سرور ارسال کنید.
همانطور که حدس زده اید، همه جادوها با استفاده از PHP و کلاس های داخلی SoapClient و SoapServer انجام می شود. خرگوش ما سرویسی برای ارسال پیامک خواهد بود.

1 بیان مشکل

1.1 مرزها

در ابتدا پیشنهاد می کنم به نتیجه ای بپردازیم که در پایان مبحث به دست خواهیم آورد. همانطور که در بالا اعلام شد سرویسی برای ارسال پیامک می نویسیم و به طور دقیق تر از منابع مختلف از طریق پروتکل SOAP پیام دریافت می کنیم. پس از آن، ما در نظر خواهیم گرفت که آنها به چه شکلی به سرور می آیند. متأسفانه فرآیند صف بندی پیام ها برای ارسال بیشتر به ارائه دهنده، به دلایل زیادی از حوصله این پست خارج است.

1.2 چه داده هایی را تغییر خواهیم داد؟

عالی است، ما در مورد مرزها تصمیم گرفته ایم! قدم بعدی که باید برداشته شود این است که تصمیم بگیریم چه داده هایی را بین سرور و مشتری مبادله کنیم. در مورد این موضوع، من پیشنهاد می کنم موها را برای مدت طولانی از هم جدا نکنید و بلافاصله به سوالات اصلی خود پاسخ دهید:
  • برای ارسال پیامک به مشترک چه حداقل داده هایی باید به سرور ارسال شود؟
  • چه حداقل داده هایی باید از سرور ارسال شود تا نیازهای مشتری را برآورده کند؟
چیزی به من می گوید که برای این باید موارد زیر را ارسال کنید:
  • شماره تلفن همراه و
  • متن پیامک
در اصل این دو ویژگی برای ارسال کافی است، اما من بلافاصله تصور می کنم که یک اس ام اس با تبریک تولد ساعت 3 یا 4 بامداد برای شما می آید! در این لحظه از همه ممنونم که مرا فراموش نکردند! بنابراین ما نیز به سرور و ارسال خواهیم کرد
  • تاریخ ارسال پیامک
مورد بعدی که می خواهم به سرور ارسال کنم این است:
  • نوع پیام
این پارامتر اجباری نیست، اما اگر سریعاً نیاز داشته باشیم به رئیس بگوییم که چه تعداد از مشتریان خود را از اخبار خود "خوشحال" کرده‌ایم و همچنین آمارهای زیبایی در این مورد ترسیم کنیم، می‌تواند برای ما بسیار مفید باشد.

و با این حال، من چیزی را فراموش کردم! اگر کمی بیشتر تأمل کنیم، شایان ذکر است که مشتری می تواند یک پیام کوتاه یا تعدادی از آنها را در یک زمان به سرور ارسال کند. به عبارت دیگر، یک بسته داده می تواند حاوی پیام هایی از یک تا بی نهایت باشد.

در نتیجه، دریافتیم که برای ارسال یک پیام کوتاه به داده های زیر نیاز داریم:

  • شماره موبایل،
  • متن پیامک،
  • زمان ارسال پیامک به مشترک،
  • نوع پیام

ما به سوال اول پاسخ دادیم، حالا باید به سوال دوم پاسخ دهیم. و شاید به خودم اجازه بدهم که کمی به هم بریزم. بنابراین از سرور فقط داده های Boolean را ارسال می کنیم که معنی آن به این معنی است:

  • درست - بسته با موفقیت به سرور رسید، احراز هویت را پشت سر گذاشت و برای ارسال به ارائه دهنده پیام کوتاه در صف قرار گرفت.
  • نادرست - در همه موارد دیگر

این توضیح بیان مشکل را به پایان می رساند! و در نهایت، بیایید به قسمت سرگرم کننده آن بپردازیم - بیایید بفهمیم این صابون چه نوع جانور عجیبی است!

2 SOAP چیست؟

به طور کلی، در ابتدا قصد نداشتم چیزی در مورد SOAP بنویسم و ​​می خواستم خودم را به پیوندهایی به وب سایت w3.org با مشخصات لازم و همچنین پیوندهایی به ویکی پدیا محدود کنم. اما در نهایت تصمیم گرفتم یک یادداشت کوتاه در مورد این پروتکل بنویسم.

و من داستان خود را با این واقعیت آغاز می کنم که این پروتکل تبادل داده متعلق به زیر مجموعه ای از پروتکل های مبتنی بر پارادایم به اصطلاح RPC (Remote Procedure Call) است که پاد پاد آن REST (انتقال حالت نمایندگی) است. شما می توانید اطلاعات بیشتری در مورد این موضوع در ویکی پدیا بخوانید. از این مقالات، ما باید موارد زیر را درک کنیم: «رویکرد RPC امکان استفاده از تعداد کمی از منابع شبکه با تعداد زیادی روش و یک پروتکل پیچیده را می‌دهد. با رویکرد REST، تعداد روش‌ها و پیچیدگی پروتکل کاملاً محدود است، به این معنی که تعداد منابع فردی می‌تواند زیاد باشد. یعنی در رابطه با ما، این بدان معناست که در مورد رویکرد RPC در سایت، همیشه یک ورودی (پیوند) به سرویس وجود خواهد داشت و چه رویه‌ای برای پردازش داده‌های ورودی که همراه با داده‌ها منتقل می‌کنیم، فراخوانی شود، در حالی که با رویکرد REST در سایت ما ورودی‌ها (پیوندها) زیادی دارد که هر کدام فقط داده‌های خاصی را می‌پذیرند و پردازش می‌کنند. اگر کسی که مطالعه می کند می داند چگونه تفاوت این رویکردها را حتی ساده تر توضیح دهد، حتما در نظرات بنویسد!

نکته بعدی که باید در مورد SOAP بدانیم این است که این پروتکل از همان XML به عنوان یک انتقال استفاده می کند که از یک طرف بسیار خوب است، زیرا زرادخانه ما بلافاصله شامل قدرت کامل مجموعه ای از فناوری های مبتنی بر این زبان نشانه گذاری است، یعنی XML-Schema - زبانی برای توصیف ساختار یک سند XML (با تشکر از ویکی پدیا!)، که امکان تأیید خودکار داده های دریافت شده توسط سرور را فراهم می کند. از مشتریان

و بنابراین، اکنون می دانیم که SOAP یک پروتکل است که برای اجرای فراخوانی های رویه از راه دور استفاده می شود و از XML به عنوان یک انتقال استفاده می کند! اگر مقاله ویکی‌پدیا را بخوانید، می‌توانید از آنجا نیز یاد بگیرید که می‌توان از آن بر روی هر پروتکل در سطح برنامه استفاده کرد، و نه فقط در ترکیب با HTTP (متاسفانه، در این مبحث فقط SOAP را در مقابل HTTP در نظر خواهیم گرفت). و می دانید چه چیزی را در این همه بیشتر دوست دارم؟ اگر هیچ حدس و گمانی وجود ندارد، پس من یک اشاره می کنم - SOAP!... هنوز هم حدس نمی زنم؟... آیا مطمئن هستید که مقاله را در ویکی پدیا می خوانید؟... به طور کلی، من شما را بیشتر شکنجه نخواهم کرد. بنابراین، من مستقیماً به پاسخ می‌روم: "SOAP (از پروتکل دسترسی به شیء ساده انگلیسی - ساده پروتکلدسترسی به اشیاء؛ تا مشخصات 1.2)". قابل توجه ترین نکته در مورد این خط به صورت ایتالیک است! من نمی دانم شما از همه اینها چه نتیجه ای گرفتید ، اما موارد زیر را می بینم - از آنجایی که این پروتکل به هیچ وجه نمی تواند "ساده" نامیده شود (و ظاهراً حتی w3 نیز با این موافق است) ، پس از نسخه 1.2 به نوعی رمزگشایی متوقف شد ! و به عنوان SOAP، just SOAP، نقطه شناخته شد.

خب، باشه، ببخشید، کمی منحرف شدم. همانطور که قبلاً نوشتم، XML به عنوان انتقال استفاده می شود و بسته هایی که بین مشتری و سرور حرکت می کنند، پاکت SOAP نامیده می شوند. اگر ساختار کلی پاکت نامه را در نظر بگیرید، برایتان بسیار آشنا به نظر می رسد، زیرا... شبیه ساختار یک صفحه HTML است. یک بخش اصلی دارد - پاکت کن، که شامل بخش هایی است سرتیترو بدن، یا عیب. که در بدنداده ها منتقل می شود و یک بخش اجباری از پاکت است، در حالی که سرتیتراختیاری است. که در سرتیترمجوز یا هر داده دیگری که مستقیماً با داده های ورودی رویه های وب سرویس مرتبط نیست ممکن است منتقل شود. در باره عیبچیز خاصی برای گفتن وجود ندارد، به جز اینکه در صورت بروز هر گونه خطایی از سرور به مشتری می رسد.

اینجاست که داستان بررسی من در مورد پروتکل SOAP به پایان می رسد (زمانی که کلاینت و سرور ما در نهایت یاد بگیرند که آنها را روی یکدیگر اجرا کنند ما به خود پاکت ها و ساختار آنها با جزئیات بیشتری نگاه خواهیم کرد) و یک مورد جدید شروع می شود - در مورد همراه SOAP به نام WSDL(زبان شرح خدمات وب). بله، بله، این همان چیزی است که بسیاری از ما را حتی از تلاش برای پیاده سازی API خود در این پروتکل می ترساند. در نتیجه، ما معمولا چرخ خود را با JSON به عنوان حمل و نقل دوباره اختراع می کنیم. پس WSDL چیست؟ WSDL زبانی برای توصیف خدمات وب و دسترسی به آنها بر اساس زبان XML (c) ویکی پدیا است. اگر این تعریف تمام معنای مقدس این فناوری را برای شما روشن نمی کند، من سعی می کنم آن را به زبان خودم توصیف کنم!

WSDL طوری طراحی شده است که به مشتریان ما اجازه می دهد تا به طور معمول با سرور ارتباط برقرار کنند. برای انجام این کار، فایل با پسوند "*.wsdl" اطلاعات زیر را شرح می دهد:

  • چه فضاهای نامی استفاده شد؟
  • چه طرحواره های داده ای استفاده شد؟
  • وب سرویس چه نوع پیام هایی را از مشتریان انتظار دارد؟
  • کدام داده متعلق به کدام رویه های وب سرویس است،
  • وب سرویس شامل چه رویه هایی است؟
  • چگونه مشتری باید رویه های خدمات وب را فراخوانی کند،
  • تماس های مشتریان باید به کدام آدرس ارسال شود؟
همانطور که می بینید، این فایل کل وب سرویس است. با مشخص کردن آدرس فایل WSDL در کلاینت، همه چیز را در مورد هر وب سرویسی خواهیم دانست! در نتیجه، نیازی نیست که مطلقاً چیزی در مورد محل قرارگیری خود وب سرویس بدانیم. تنها چیزی که باید بدانید محل فایل WSDL آن است! به زودی متوجه خواهیم شد که صابون به اندازه ضرب المثل های روسی ترسناک نیست.

3 مقدمه ای بر XML-Schema

اکنون ما چیزهای زیادی در مورد چیستی SOAP، آنچه در داخل آن وجود دارد، می دانیم و یک مرور کلی از پشته فناوری که آن را احاطه کرده است داریم. از آنجایی که اول از همه، SOAP یک روش تعامل بین یک کلاینت و یک سرور است و زبان نشانه گذاری XML به عنوان یک انتقال برای آن استفاده می شود، در این بخش کمی در مورد چگونگی اعتبارسنجی خودکار داده ها با استفاده از طرحواره های XML خواهیم فهمید.

وظیفه اصلی نمودار توصیف ساختار داده هایی است که قرار است پردازش کنیم. تمام داده ها در طرحواره های XML به دو دسته تقسیم می شوند ساده(اسکالر) و مجتمع(ساختارها) انواع. انواع ساده شامل انواع زیر است:

  • خط،
  • عدد،
  • مقدار بولی،
  • تاریخ.
چیزی بسیار ساده که هیچ پسوندی در داخل آن وجود ندارد. آنتی پاد آنها از انواع پیچیده پیچیده است. ساده ترین نمونه از انواع پیچیده که به ذهن همه می رسد، اشیا هستند. مثلا یک کتاب. این کتاب شامل خواص: نویسنده, نام, قیمت, شماره شابکو غیره. و این ویژگی ها به نوبه خود می توانند انواع ساده یا پیچیده باشند. و وظیفه طرحواره XML توصیف این است.

پیشنهاد می کنم راه دور نرویم و برای پیامک ما یک طرح XML بنویسیم! در زیر توضیحات xml پیام اس ام اس آمده است:

71239876543 پیام آزمایشی 2013-07-20T12:00:00 12
نمودار نوع پیچیده ما به صورت زیر خواهد بود:


این ورودی به شرح زیر است: ما یک متغیر داریم " پیام"نوع" پیام"و یک نوع پیچیده وجود دارد به نام " پیام"، که از مجموعه ای متوالی از عناصر تشکیل شده است" تلفن"تایپ کنید رشته, « متن"تایپ کنید رشته, « تاریخ"تایپ کنید زمان قرار, « نوع"تایپ کنید اعشاری. این انواع ساده هستند و قبلاً در توضیحات طرحواره تعریف شده اند. تبریک می گویم! ما اولین طرح XML خود را نوشتیم!

من فکر می کنم که معنای عناصر " عنصر"و" نوع پیچیده"همه چیز کم و بیش برای شما روشن شده است، بنابراین ما دیگر روی آنها تمرکز نمی کنیم و بیایید مستقیماً به عنصر آهنگساز برویم." توالی" وقتی از عنصر آهنگساز استفاده می کنیم " توالی"به شما اطلاع می دهیم که عناصر موجود در آن باید همیشه به ترتیب مشخص شده در نمودار قرار گیرند و همه آنها اجباری هستند. اما ناامید نشو! دو عنصر آهنگساز دیگر در طرحواره های XML وجود دارد: انتخاب"و" همه" آهنگساز" انتخاب"اعلام می کند که باید یکی از عناصر ذکر شده در آن وجود داشته باشد و آهنگساز" همه» – هر ترکیبی از عناصر فهرست شده.

همانطور که به یاد دارید، در بخش اول موضوع توافق کردیم که از یک تا بی نهایت پیامک ها را می توان در یک بسته منتقل کرد. بنابراین، من پیشنهاد می کنم درک کنیم که چگونه چنین داده هایی در طرح XML اعلام می شوند. ساختار کلی بسته ممکن است به شکل زیر باشد:

71239876543 پیام آزمایشی 1 2013-07-20T12:00:00 12 71239876543 پیام آزمایشی N 2013-07-20T12:00:00 12
نمودار چنین نوع پیچیده ای به صورت زیر است:


بلوک اول حاوی اعلان آشنا از نوع پیچیده است. پیام" اگر متوجه شدید، پس در هر نوع ساده موجود در " پیام"، ویژگی های شفاف کننده جدید اضافه شده است" کوچک اتفاق می افتد"و" maxOccurs" همانطور که ممکن است از نام آن حدس بزنید، اولین ( کوچک اتفاق می افتد) نشان می دهد که این دنباله باید حداقل دارای یک عنصر از نوع " تلفن», « متن», « تاریخ"و" نوع"، در حالی که بعدی ( maxOccurs) ویژگی به ما اعلام می کند که حداکثر یک عنصر از این قبیل در دنباله ما وجود دارد. در نتیجه، هنگامی که طرحواره های خود را برای هر داده ای می نویسیم، در مورد نحوه پیکربندی آنها بیشترین انتخاب را به ما داده می شود!

بلوک دوم نمودار عنصر " را اعلام می کند لیست پیام ها"نوع" MessageList" واضح است که " MessageList"یک نوع پیچیده است که شامل حداقل یک عنصر است" پیام"، اما حداکثر تعداد این عناصر محدود نیست!

4 WSDL خود را بنویسید

آیا به یاد دارید که WSDL سرویس وب ما است؟ امیدوارم یادت بیاد! همانطور که ما آن را می نویسیم، وب سرویس کوچک ما روی آن اجرا می شود. بنابراین، من پیشنهاد می کنم که در اطراف خود قاطی نکنید.

به طور کلی، برای اینکه همه چیز برای ما درست کار کند، باید یک فایل WSDL با نوع MIME صحیح را به مشتری منتقل کنیم. برای انجام این کار، باید وب سرور خود را بر اساس آن پیکربندی کنید، یعنی نوع MIME را برای فایل هایی با پسوند "*.wsdl" روی خط زیر تنظیم کنید:

برنامه/wsdl+xml
اما در عمل، من معمولا هدر HTTP را از طریق PHP ارسال می کنم. متن/xml»:

Header("Content-Type: text/xml; charset=utf-8");
و همه چیز عالی کار کرد!

می خواهم فوراً به شما هشدار دهم که وب سرویس ساده ما توضیحات نسبتاً چشمگیری خواهد داشت ، بنابراین نگران نباشید ، زیرا ... بیشتر متن آب اجباری است و با یک بار نوشتن می توانید مدام آن را از یک وب سرویس به سرویس دیگر کپی کنید!

از آنجایی که WSDL XML است، باید مستقیماً در خط اول در مورد آن بنویسید. عنصر ریشه فایل همیشه باید نامگذاری شود تعاریف»:


به طور معمول، WSDL از 4-5 بلوک اصلی تشکیل شده است. اولین بلوک، تعریف وب سرویس یا به عبارت دیگر نقطه ورود است.


اینجا می گوید که ما یک سرویس داریم به نام " SmsService" در اصل، تمام نام های موجود در فایل WSDL می تواند توسط شما به هر چیزی که می خواهید تغییر کند، زیرا آنها مطلقاً هیچ نقشی ندارند.

پس از این ما اعلام می کنیم که در وب سرویس ما " SmsServiceیک نقطه ورود ("پورت") به نام " SmsServicePort" به این نقطه ورود است که تمام درخواست های مشتریان به سرور ارسال می شود. و در عنصر « نشانی» پیوند به فایل کنترل کننده ای که درخواست ها را می پذیرد.

هنگامی که وب سرویس را تعریف کردیم و نقطه ورودی آن را مشخص کردیم، باید رویه های پشتیبانی شده را به آن متصل کنیم:


برای انجام این کار، لیستی از عملیات و به چه شکلی که آنها را فراخوانی می کنند، می کند. آن ها برای بندر " SmsServicePort"یک الزام آور تحت نام تعریف شده است" SMSServiceBinding"، که یک نوع تماس دارد" rpcو HTTP به عنوان پروتکل انتقال استفاده می شود. بنابراین، در اینجا نشان دادیم که یک تماس RPC از طریق HTTP برقرار خواهیم کرد. پس از این ما توضیح می دهیم که کدام رویه ها ( عمل) در وب سرویس پشتیبانی می شوند. ما فقط از یک روش پشتیبانی خواهیم کرد - " ارسال پیامک" از طریق این روش پیام های فوق العاده ما به سرور ارسال می شود! پس از اعلام رویه، باید مشخص شود که داده ها به چه شکلی منتقل می شوند. در این مورد، نشان داده شده است که از پاکت های استاندارد SOAP استفاده خواهد شد.

پس از آن، باید رویه را به پیام‌ها متصل کنیم:


برای این کار مشخص می کنیم که binding ما از نوع " SMSServicePortType"و در عنصر" portType"با نامی از همان نوع، ما اتصال رویه ها به پیام ها را نشان می دهیم. و بنابراین، پیام دریافتی (از مشتری به سرور) نامیده می شود sendSmsRequest"، و خروجی (از سرور به مشتری)" sendSmsResponse" مانند همه نام‌ها در WSDL، نام پیام‌های ورودی و خروجی دلخواه است.

حال باید خود پیام ها را شرح دهیم، یعنی. ورودی و خروجی:


برای این کار ما عناصر را اضافه می کنیم " پیام"با اسامی" sendSmsRequest"و" sendSmsResponse" به ترتیب. در آنها نشان می دهیم که ورودی باید یک پاکت باشد که ساختار آن با نوع داده مطابقت دارد. درخواست" پس از آن یک پاکت از سرور حاوی نوع داده بازگردانده می شود - " واکنش».

اکنون باید کمی انجام دهیم - شرحی از این انواع را به فایل WSDL خود اضافه کنیم! و به نظر شما WSDL داده های ورودی و خروجی را چگونه توصیف می کند؟ فکر می‌کنم مدت‌ها پیش همه چیز را فهمیده‌اید و به خود گفته‌اید که با استفاده از طرحواره‌های XML! و کاملا حق با شما خواهد بود!


می توانید به ما تبریک بگویید! اولین WSDL ما نوشته شده است! و ما یک قدم به رسیدن به هدفمان نزدیکتر شده ایم.
در مرحله بعد، به آنچه PHP برای توسعه برنامه های کاربردی توزیع شده خودمان در اختیار ما قرار می دهد، خواهیم دید.

5 اولین سرور SOAP ما

قبلاً نوشتم که برای ایجاد یک سرور SOAP در PHP از کلاس SoapServer داخلی استفاده خواهیم کرد. برای اینکه تمام اقدامات بعدی مانند من اتفاق بیفتد، باید PHP خود را کمی تغییر دهید. برای دقیق تر بودن، باید مطمئن شوید که پسوند "php-soap" را نصب کرده اید. بهتر است نحوه نصب آن را بر روی وب سرور خود در وب سایت رسمی PHP بخوانید (لیست مراجع را ببینید).

بعد از اینکه همه چیز نصب و پیکربندی شد، باید یک فایل در پوشه اصلی هاست شما ایجاد کنیم. smsservice.php» با محتوای زیر:

setClass ("SoapSmsGateWay"); //سرور را راه اندازی کنید $server->handle();
امیدوارم نیازی به توضیح آنچه در بالای خط با تابع "ini_set" وجود دارد نباشد. زیرا در آنجا مشخص می شود که کدام هدرهای HTTP را از سرور به مشتری ارسال کنیم و محیط پیکربندی می شود. در خط "ini_set" ما کش کردن فایل WSDL را غیرفعال می کنیم تا تغییرات ما در آن بلافاصله بر روی مشتری اعمال شود.

حالا میرسیم به سرور! همانطور که می بینید، کل سرور SOAP فقط سه خط طول می کشد! در خط اول، یک نمونه جدید از شی SoapServer ایجاد می کنیم و آدرس توضیحات WSDL سرویس وب را به سازنده آن ارسال می کنیم. اکنون می دانیم که در ریشه هاست در فایلی با نام خود توضیحی قرار خواهد گرفت. smsservice.wsdl.php" در خط دوم، به سرور SOAP می گوییم که کدام کلاس باید کشیده شود تا پاکت دریافت شده از مشتری را پردازش کند و پاکت را با پاسخ برگرداند. همانطور که ممکن است حدس بزنید، در این کلاس است که تنها روش ما توضیح داده خواهد شد ارسال پیامک. در خط سوم سرور را راه اندازی می کنیم! همین، سرور ما آماده است! که با آن به همه ما تبریک می گویم!

حال باید فایل WSDL را ایجاد کنیم. برای انجام این کار، می توانید به سادگی محتویات آن را از قسمت قبلی کپی کنید، یا آزادانه عمل کنید و کمی آن را "الگو" کنید:

"; ?> /" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:soap12="http://schemas.xmlsoap.org/wsdl/soap12/" xmlns:http="http:// schemas.xmlsoap.org/wsdl/http/" name="SmsWsdl" xmlns="http://schemas.xmlsoap.org/wsdl/"> /"> /smsservice.php" />
در این مرحله باید از سرور حاصل رضایت کامل داشته باشیم، زیرا می‌توانیم پاکت‌هایی را که به سمت آن می‌آیند ثبت کنیم و سپس با آرامش داده‌های دریافتی را تجزیه و تحلیل کنیم. برای اینکه بتوانیم هر چیزی را روی سرور دریافت کنیم، به یک کلاینت نیاز داریم. پس اجازه بدهید به این کار برسیم!

6 مشتری SOAP در راه است

اول از همه باید فایلی بسازیم که در آن کلاینت را بنویسیم. طبق معمول، آن را در ریشه هاست ایجاد می کنیم و آن را " می نامیم. client.php"، و در داخل ما موارد زیر را می نویسیم:

messageList = new MessageList(); $req->messageList->message = new Message(); $req->messageList->message->phone = "79871234567"; $req->messageList->message->text = "تست پیام 1"; $req->messageList->message->date = "2013-07-21T15:00:00.26"; $req->messageList->message->type = 15; $client = new SoapClient("http://($_SERVER["HTTP_HOST"])/smsservice.wsdl.php، array("soap_version" => SOAP_1_2)); var_dump($client->sendSms($req));
بیایید اشیاء خود را توصیف کنیم. هنگامی که ما WSDL را نوشتیم، سه موجودیت را برای پاکت ورودی به سرور توصیف کرد: درخواست, MessageListو پیام. بر این اساس کلاس ها درخواست, MessageListو پیامبازتابی از این موجودات در اسکریپت PHP ما هستند.

هنگامی که ما اشیاء را تعریف کردیم، باید یک شی ایجاد کنیم ( $req) که به سرور ارسال می کنیم. پس از آن دو خط محبوب ترین برای ما می آیند! مشتری SOAP ما! باور کنید یا نه، این برای سرور ما برای شروع دریافت پیام از مشتری و همچنین برای سرور ما برای دریافت و پردازش موفقیت آمیز آنها کافی است! در اولین مورد، یک نمونه از کلاس SoapClient ایجاد می کنیم و آدرس محل فایل WSDL را به سازنده آن ارسال می کنیم و در پارامترها به صراحت نشان می دهیم که با استفاده از پروتکل SOAP نسخه 1.2 کار خواهیم کرد. در خط بعدی متد را فراخوانی می کنیم ارسال پیامکهدف - شی مشتری $و بلافاصله نتیجه را در مرورگر نمایش دهید.
بیایید آن را اجرا کنیم و ببینیم در نهایت چه چیزی به دست آوردیم!

شی زیر از سرور به من برگردانده شد:

Object(stdClass) public "status" => boolean true
و این عالی است، زیرا ... اکنون ما با اطمینان می دانیم که سرور ما کار می کند و نه تنها کار می کند، بلکه می تواند مقادیری را به مشتری برگرداند!

حال بیایید به گزارشی که با احتیاط در سمت سرور نگه می داریم نگاه کنیم! در قسمت اول آن، داده های خامی را می بینیم که به سرور رسیده است:

79871234567 پیام آزمایشی 1 2013-07-21T15:00:00.26 15
این پاکت است. حالا شما می دانید که چگونه به نظر می رسد! اما بعید است که ما علاقه مند باشیم که همیشه به آن نگاه کنیم، بنابراین بیایید شی را از فایل log از سریال خارج کنیم و ببینیم آیا همه چیز خوب است یا خیر:

Object(stdClass) public "messageList" => object(stdClass) public "message" => object(stdClass) public "phone" => string "79871234567" (length=11) public "text" => string "Test message 1" " (length=37) public "date" => string "2013-07-21T15:00:00.26" (length=22) public "type" => string "15" (length=2)
همانطور که می بینید، شی به درستی deserialized شد، که می خواهم به همه ما تبریک بگویم! چیز جالب تری در آینده در انتظار ما است! یعنی کلاینت را نه فقط یک پیام کوتاه بلکه یک بسته کامل (به عبارت دقیق تر، سه) به سرور ارسال می کنیم!

7 ارسال اشیاء پیچیده

بیایید به این فکر کنیم که چگونه می توانیم یک دسته کامل از پیام ها را در یک بسته به سرور منتقل کنیم؟ احتمالاً ساده ترین راه، سازماندهی یک آرایه در داخل عنصر messageList خواهد بود! بیا انجامش بدیم:

// ایجاد یک شی برای ارسال به سرور $req = new Request(); $req->messageList = new MessageList(); $msg1 = new Message(); $msg1->phone = "79871234567"; $msg1->text = "پیام آزمایشی 1"; $msg1->date = "2013-07-21T15:00:00.26"; $msg1->type = 15; $msg2 = new Message(); $msg2->phone = "79871234567"; $msg2->text = "پیام آزمایشی 2"; $msg2->date = "2014-08-22T16:01:10"; $msg2->type = 16; $msg3 = new Message(); $msg3->phone = "79871234567"; $msg3->text = "پیام آزمایشی 3"; $msg3->date = "2014-08-22T16:01:10"; $msg3->type = 17; $req->messageList->message = $msg1; $req->messageList->message = $msg2; $req->messageList->message = $msg3;
گزارش های ما نشان می دهد که بسته زیر از مشتری دریافت شده است:

79871234567 پیام آزمایشی 1 2013-07-21T15:00:00.26 15 79871234567 پیام تست 2 2014-08-22T16:01:10 16 79871234567 پیام تست 3 2014-08-22T16:01:10 17
چه مزخرفی، شما می گویید؟ و به نوعی حق با شماست، زیرا... به محض اینکه متوجه شدیم یک شی از کلاینت خارج شده است، کاملاً به همان شکل در قالب یک پاکت به سرور ما آمد. درست است، پیام‌های اس ام اس در XML آنطور که ما نیاز داشتیم سریال نمی‌شدند - آنها باید در عناصر پیچیده می‌شدند. پیام، نه در ساختار. حال بیایید ببینیم که چنین شیئی به چه شکلی به روش می آید ارسال پیامک:

Object(stdClass) public "messageList" => object(stdClass) public "message" => object(stdClass) public "Struct" => array (size=3) 0 => object(stdClass) public "phone" => string "79871234567" (length=11) public "text" => string "Test message 1" (length=37) public "date" => string "2013-07-21T15:00:00.26" (length=22) public " type" => string "15" (length=2) 1 => object(stdClass) public "phone" => string "79871234567" (length=11) public "text" => string "Test message 2" (length= 37) public "date" => string "2014-08-22T16:01:10" (length=19) public "type" => string "16" (length=2) 2 => object(stdClass) public "phone " => string "79871234567" (length=11) public "text" => string "Test message 3" (length=37) public "date" => string "2014-08-22T16:01:10" (length= 19) عمومی "type" => رشته "17" (طول = 2)
این دانش چه چیزی به ما می دهد؟ فقط مسیری که انتخاب کرده‌ایم درست نیست و پاسخی برای این سوال دریافت نکرده‌ایم - "چگونه می‌توانیم ساختار داده صحیح را روی سرور دریافت کنیم؟" اما من پیشنهاد می کنم ناامید نشویم و سعی کنیم آرایه خود را به نوع تبدیل کنیم یک شی:

$req->messageList->message = (object)$req->messageList->message;
در این صورت، پاکت دیگری دریافت خواهیم کرد:

79871234567 پیام آزمایشی 1 2013-07-21T15:00:00.26 15 79871234567 پیام تست 2 2014-08-22T16:01:10 16 79871234567 پیام تست 3 2014-08-22T16:01:10 17
به روش رسید ارسال پیامکشی دارای ساختار زیر است:

Object(stdClass) public "messageList" => object(stdClass) public "message" => object(stdClass) public "BOGUS" => array (size=3) 0 => object(stdClass) public "phone" => string "79871234567" (length=11) public "text" => string "Test message 1" (length=37) public "date" => string "2013-07-21T15:00:00.26" (length=22) public " type" => string "15" (length=2) 1 => object(stdClass) public "phone" => string "79871234567" (length=11) public "text" => string "Test message 2" (length= 37) public "date" => string "2014-08-22T16:01:10" (length=19) public "type" => string "16" (length=2) 2 => object(stdClass) public "phone " => string "79871234567" (length=11) public "text" => string "Test message 3" (length=37) public "date" => string "2014-08-22T16:01:10" (length= 19) عمومی "type" => رشته "17" (طول = 2)
در مورد من، "مجموع از تغییر مکان اصطلاحات تغییر نمی کند" (ج). چی جعلی، چی ساختار- ما هنوز به هدف خود نرسیدیم! و برای رسیدن به آن، باید مطمئن شویم که به جای این نام های نامفهوم، نام اصلی ما نمایش داده شود. پیام. اما نویسنده هنوز نمی داند چگونه به این امر دست یابد. بنابراین، تنها کاری که می توانیم انجام دهیم این است که از شر ظرف اضافی خلاص شویم. به عبارت دیگر، ما اکنون مطمئن خواهیم شد که به جای پیامتبدیل شد جعلی! برای انجام این کار، شی را به صورت زیر تغییر دهید:

// ایجاد یک شی برای ارسال به سرور $req = new Request(); $msg1 = new Message(); $msg1->phone = "79871234567"; $msg1->text = "پیام آزمایشی 1"; $msg1->date = "2013-07-21T15:00:00.26"; $msg1->type = 15; $msg2 = new Message(); $msg2->phone = "79871234567"; $msg2->text = "پیام آزمایشی 2"; $msg2->date = "2014-08-22T16:01:10"; $msg2->type = 16; $msg3 = new Message(); $msg3->phone = "79871234567"; $msg3->text = "پیام آزمایشی 3"; $msg3->date = "2014-08-22T16:01:10"; $msg3->type = 17; $req->messageList = $msg1; $req->messageList = $msg2; $req->messageList = $msg3; $req->messageList = (object)$req->messageList;
اگر خوش شانس باشیم و نام صحیح از نمودار بیرون بیاید چه؟ برای انجام این کار، بیایید به پاکت ارسال شده نگاه کنیم:

79871234567 پیام آزمایشی 1 2013-07-21T15:00:00.26 15 79871234567 پیام تست 2 2014-08-22T16:01:10 16 79871234567 پیام تست 3 2014-08-22T16:01:10 17
بله، معجزه ای اتفاق نیفتاد! جعلی- ما برنده نخواهیم شد! بیا به ارسال پیامکشی در این حالت به شکل زیر خواهد بود:

Object(stdClass) public "messageList" => object(stdClass) public "BOGUS" => array (size=3) 0 => object(stdClass) public "phone" => string "79871234567" (length=11) public " text" => رشته "پیام آزمایشی 1" (طول = 37) عمومی "تاریخ" => رشته "2013-07-21T15:00:00.26" (طول=22) عمومی "نوع" => رشته "15" (طول =2) 1 => object(stdClass) public "phone" => string "79871234567" (length=11) public "text" => string "Test message 2" (length=37) public "date" => string " 2014-08-22T16:01:10" (طول = 19) عمومی "type" => رشته "16" (طول=2) 2 => شی (stdClass) عمومی "phone" => رشته "79871234567" (طول= 11) public "text" => string "Test message 3" (length=37) public "date" => string "2014-08-22T16:01:10" (length=19) public "type" => string " 17 اینچ (طول = 2)
همانطور که می گویند - "تقریبا"! در این یادداشت (کمی غم انگیز)، من پیشنهاد می کنم به آرامی همه چیز را جمع بندی کنیم و برای خودمان نتیجه گیری کنیم.

8 نتیجه گیری

بالاخره به اینجا رسیدیم! بیایید بفهمیم که اکنون چه کاری می توانید انجام دهید:
  • می توانید فایل WSDL لازم برای وب سرویس خود را بنویسید.
  • شما به راحتی می توانید مشتری خود را بنویسید که می تواند از طریق SOAP با سرور ارتباط برقرار کند.
  • شما می توانید سرور خود را بنویسید که از طریق SOAP با دنیای خارج ارتباط برقرار می کند.
  • شما می توانید آرایه هایی از همان نوع اشیاء را از مشتری خود به سرور ارسال کنید (با برخی محدودیت ها).
ما همچنین در طی تحقیقات کوچک خود به کشفیاتی دست یافتیم:
  • کلاس SoapClient بومی ساختارهای داده ای از همان نوع را در XML به درستی سریال سازی نمی کند.
  • هنگام سریال سازی یک آرایه به XML یک عنصر اضافی به نام ایجاد می کند ساختار;
  • هنگام سریال سازی یک شی در XML یک عنصر اضافی به نام ایجاد می کند جعلی;
  • جعلیبدتر از ساختاربا توجه به این واقعیت که پاکت نامه فشرده تر است (فضای نام اضافی به هدر XML پاکت اضافه نمی شود).
  • متأسفانه، کلاس SoapServer به طور خودکار داده های پاکت را با طرح XML ما تأیید نمی کند (شاید سرورهای دیگر نیز این کار را انجام نمی دهند).

من روی این سوال که آن چیست نمی پردازم خدمات وبو چرا به آنها نیاز است. مقالات زیادی در این زمینه در اینترنت وجود دارد. من فقط سعی می کنم به طور خلاصه نشان دهم که ایجاد یک کلاینت برای هر وب سرویس در PHP چقدر ساده است.

تنظیمات

برای استفاده صابوندر php باید ماژول SOAP را (که در توزیع php5 موجود است) وصل کنید. در ویندوز، این کار به سادگی انجام می شود - باید اضافه کنید (یعنی اضافه کنید، زیرا این خط فقط در آنجا توضیح داده نمی شود، بلکه به طور کلی وجود ندارد) php.ini:
extension=php_soap.dll

اگر php را به عنوان ماژول نصب کرده اید، فراموش نکنید که سرور را مجددا راه اندازی کنید.


ایجاد یک کلاینت SOAP از یک سند WSDL

ایجاد یک کلاینت SOAP معمولاً توسط سند WSDL، که یک سند XML در قالب خاصی است که به طور کامل یک وب سرویس خاص را توصیف می کند. برای جزئیات در مورد WSDL، من شما را به وب سایت کنسرسیوم W3C ارجاع می دهم - http://www.w3.org/TR/2005/WD-wsdl20-soap11-binding-20050510/.

نکته اصلی که برای ساختن یک کلاینت برای یک وب سرویس باید بدانید این است که URL سند WSDL آن را بدانید.
به عنوان مثال، بیایید وب سرویس "نرخ تبادل ارز" را از xmethods.com در نظر بگیریم. آدرس این وب سرویس که امکان دریافت آنلاین نرخ ارز را به شما می دهد http://www.xmethods.net/sd/2001/CurrencyExchangeService.wsdl است.

نکته مهم دوم این است که از توضیحات وب سرویس باید اطلاعاتی در مورد روش هایی که این سرویس ارائه می دهد و چه پارامترهایی را به عنوان مقادیر ورودی به آن منتقل کنیم (بسیار شبیه فراخوانی یک تابع یا کلاس معمولی PHP) به دست می آید. روش). معمولاً این اطلاعات در توضیحات سرویس در وب سایت آن موجود است. وب سرویس ما برای به دست آوردن نرخ ارز متد getRate() را ارائه می دهد که کدهای ارز به عنوان آرگومان ارسال می شوند.

و در آخر، مهم است که بدانیم چه چیزی را باید به عنوان پاسخ انتظار داشت: چند مقدار، چه نوع و غیره. این را نیز می توان از توضیحات بدست آورد.
و در نتیجه، کد بسیار ساده و فشرده، تقریبا ابتدایی به نظر می رسد:

// با استفاده از وب سرویس
// "نرخ تبادل ارز" از xmethods.com

// ایجاد یک سرویس گیرنده SOAP از یک سند WSDL
$client = new SoapClient("http://www.xmethods.net/sd/2001/CurrencyExchangeService.wsdl");

// یک درخواست SOAP ارسال کنید و نتیجه را دریافت کنید
$result = $client->getRate("us", "russia");

Echo 'نرخ مبادله دلار فعلی:'، $نتیجه، 'روبل';
?>

همانطور که از کد می بینید، باید URL سند WSDL را به سازنده کلاس SoapClient ارسال کنید و یک شی را برای کار با وب سرویس مورد نظر دریافت کنید. سپس متدی از این شی فراخوانی می شود که نام آن با نام خود متد وب سرویس یکسان است. این روش نتیجه مورد نظر ما را برمی گرداند.

بنابراین، این مثال ساده اصل ساخت یک کلاینت SOAP برای خدمات وب در PHP را نشان می دهد. با این حال، در یک برنامه واقعی هنوز چیزهای زیادی برای مراقبت وجود دارد، به ویژه این واقعیت که وقتی وب سرویس فراخوانی می شود، ممکن است به طور موقت در دسترس نباشد یا خطایی را برگرداند. استفاده از بلوک به وضوح خود را نشان می دهد امتحان کردن/گرفتن/پرتاب کردن :)

اینجا در LeaseWeb، ما با خدمات وب SOAP کار می کنیم تا برنامه های داخلی خود را با یکدیگر یکپارچه کنیم. به خصوص در طول توسعه و آزمایش برنامه های ما زیرا ما به توانایی تمرین با SOAP API نیاز داریم.

$ curl -sS http://leaseweb.github.io/php-soap-client/installer | php

با این کار فایل phار در دایرکتوری کاری فعلی دانلود می‌شود و آن را قابل اجرا می‌کند، بنابراین می‌توانید بلافاصله با فراخوانی از آن استفاده کنید:

$ ./soap_client

برای نصب آخرین نسخه اصلی، می‌توانید کد منبع را مستقیماً از GitHub دریافت کنید، فایل .phar خود را بسته بندی کنید و آن را با استفاده از GNU Make نصب کنید.
برای اینکه بتوانید فایل .phar را بسازید باید composer را نصب کنید. برای مطالعه بیشتر در مورد آهنگساز به مستندات عالی آنها مراجعه کنید.

# php soap client را نصب کنید $ git clone https://github.com/LeaseWeb/php-soap-client.git $ cd php-soap-client $ composer.phar install $ make $ sudo make install

اگر در حین اجرا یک استثناء Failed to compile phar دریافت می کنید، باید phar.readonly = Off را در php.ini خود تنظیم کنید. در یک ماشین توسعه، انجام این کار خوب است، اما لطفاً هنگام تنظیم phar.readonly روی Off، از خطرات امنیتی آگاه باشید.

دستور make install بالا برنامه soap_client را در /usr/local/bin نصب می‌کند و آن را قابل اجرا می‌کند، بنابراین می‌توانید به راحتی آن را به این صورت فراخوانی کنید:

$ soap_client php-soap-client نسخه 2.1.3 استفاده: فرمان گزینه‌ها: ... دستورات موجود: تماس با سرویس راه دور با «روش» مشخص شده تماس بگیرید و پاسخ به stdout را خروجی بگیرید. help نمایش راهنما برای فهرست دستورات فهرست دستورات فهرست روش‌ها فهرستی از روش‌های موجود برای فراخوانی از راه دور دریافت کنید. درخواست یک درخواست SOAP با فرمت xml برای متد داده شده و خروجی stdout ایجاد کنید. wsdl WSDL یک سرویس صابون را دریافت کنید.

از این مرحله به بعد، فرض می کنیم که شما soap_client.phar را در /usr/local/bin/soap_client بر روی سیستم خود نصب کرده اید و دایرکتوری /urs/local/bin در $PATH شما قرار دارد.

فرض کنید می‌خواهیم ببینیم چه روش‌هایی در سرویس راه دور http://www.webservicex.net/ConvertTemperature.asmx موجود است. می توانیم دستور زیر را صادر کنیم:

فهرست-روش‌های $ soap_client --endpoint="http://www.webservicex.net/ConvertTemperature.asmx?WSDL"

که خروجی زیر را خواهد داشت:

ConvertTemp

اگر دستور بالا را با گزینه -vvv اجرا کنید، خروجی پرمخاطب تری خواهید داشت.
در این مورد تنها روش موجود ConvertTemp است. بیایید ببینیم که یک درخواست SOAP XML برای این روش چگونه به نظر می رسد:

$ soap_client --endpoint="http://www.webservicex.net/ConvertTemperature.asmx?WSDL" درخواست ConvertTemp 0

اگر می‌خواهید یک درخواست SOAP به روش ConvertTemp در سرویس راه دور ارسال کنید، از دستور فراخوانی فرعی استفاده کنید:

$ soap_client --endpoint="http://www.webservicex.net/ConvertTemperature.asmx?WSDL" تماس --editor ConvertTemp

بعد از دستور call sub به گزینه --editor توجه کنید. اگر از --editor flag استفاده می کنید soap_client ویرایشگر مشخص شده در متغیر محیطی شما $EDITOR را باز می کند تا بتوانید درخواست XML را قبل از ارسال تغییر دهید.

اگر چندین بار یک درخواست را صادر کنید، می توانید یک درخواست صابون را به عنوان یک فایل XML محلی ذخیره کنید و آن را به /dev/stdin فرمان فراخوانی soap_client ارسال کنید:

# درخواست xml را دریافت کنید و آن را به صورت محلی ذخیره کنید $ soap_client --endpoint="http://www.webservicex.net/ConvertTemperature.asmx?WSDL" درخواست ConvertTemp > my_sample_request.xml # اکنون my_sample_request.xml را ویرایش کنید # اکنون می توانید با روش ConvertTemp با این درخواست از پیش آماده شده $ soap_client --endpoint="http://www.webservicex.net/ConvertTemperature.asmx?WSDL" با ConvertTemp تماس بگیرید< my_sample_request.xml

از آنجایی که هنگام کاوش در یک وب سرویس راه دور، دستورات soap_client را مکرراً در مدت کوتاهی تکرار خواهید کرد، می‌توانید با تنظیم یک متغیر محیطی SOAPCLIENT_ENDPOINT که حاوی URL به WSDL است، در زمان خود صرفه‌جویی کنید. هنگامی که این متغیر محیطی تنظیم می شود، می توانید گزینه خط فرمان --endpoint را حذف کنید. بیایید این کار را اکنون انجام دهیم و متد ConvertTemp را فراخوانی کنیم:

$ export SOAPCLIENT_ENDPOINT="http://www.webservicex.net/ConvertTemperature.asmx?WSDL" $ soap_client تماس ConvertTemp< my_sample_request.xml

می خواستم بدانم 107.6 درجه فارنهایت چقدر است، بنابراین my_sample_request.xml من شامل موارد زیر است:

$ cat my_sample_request.xml 107.6 درجه فارنهایت درجه سلسیوس

$ soap_client با ConvertTemp تماس بگیرید< my_sample_request.xml stdClass Object ( => 42)

جواب 42 است.

اگر ترجیح می دهید پاسخ ها را در قالب XML ببینید، می توانید از گزینه خط فرمان --xml استفاده کنید:

$ soap_client تماس --xml ConvertTemp< my_sample_request.xml 42

این آموزش باید اطلاعات کافی برای شروع کاوش، آزمایش و/یا توسعه SOAP API در اختیار شما قرار دهد.
در پست بعدی وبلاگ، موضوع مشتری صابون php را ادامه خواهم داد. ما در حال حاضر روی بسته بندی آرشیو .phar برای وب کار می کنیم.

بخش غنایی.

تصور کنید که سیستم خاصی را پیاده سازی کرده اید یا در حال پیاده سازی هستید که باید از بیرون قابل دسترسی باشد. آن ها سرور خاصی وجود دارد که باید با آن ارتباط برقرار کنید. به عنوان مثال یک وب سرور.

این سرور می تواند اقدامات زیادی را انجام دهد، با پایگاه داده کار کند، برخی از درخواست های شخص ثالث را به سرورهای دیگر انجام دهد، محاسباتی را انجام دهد و غیره. طبق سناریویی که او شناخته شده است (یعنی بر اساس سناریوی توسعه دهندگان) زندگی کند و احتمالاً توسعه یابد. ارتباط شخصی با چنین سروری جالب نیست، زیرا ممکن است نتواند/نخواهد صفحات زیبایی با تصاویر و سایر محتوای کاربرپسند ارائه دهد. نوشته شده و کار می کند تا زمانی که از آن خواسته می شود کار کند و داده ها را ارائه دهد، بدون اینکه نگران خوانایی آن توسط انسان باشد، مشتری خودش با آن برخورد می کند.

سایر سیستم‌ها با دسترسی به این سرور، می‌توانند داده‌های دریافتی از این سرور را به صلاحدید خود دفع کنند - پردازش، جمع‌آوری، ارسال به مشتریان خود و غیره.

خوب یکی از گزینه های ارتباط با چنین سرورهایی SOAP است. پروتکل تبادل پیام SOAP xml.

بخش عملی

یک وب سرویس (این نام چیزی است که سرور ارائه می دهد و مشتریان از آن استفاده می کنند) امکان برقراری ارتباط با سرور را با پیام هایی با ساختار واضح فراهم می کند. واقعیت این است که وب سرویس هیچ داده ای را نمی پذیرد. وب سرویس به هر پیامی که با قوانین مطابقت نداشته باشد با خطا پاسخ می دهد. ضمناً خطا به شکل xml با ساختار واضح نیز خواهد بود (که در مورد متن پیام صادق نیست).

WSDL (زبان شرح خدمات وب). قوانینی که بر اساس آن پیام ها برای وب سرویس ایجاد می شوند نیز با استفاده از xml توضیح داده شده اند و همچنین ساختار واضحی دارند. آن ها اگر یک وب سرویس توانایی فراخوانی یک متد را فراهم می کند، باید به مشتریان اجازه دهد تا بدانند چه پارامترهایی برای این روش استفاده می شود. اگر وب سرویس یک رشته برای Method1 به عنوان پارامتر انتظار داشته باشد و رشته باید Param1 نامیده شود، این قوانین در توضیحات وب سرویس مشخص می شوند.

نه تنها انواع ساده، بلکه اشیا و مجموعه ای از اشیاء را نیز می توان به عنوان پارامتر ارسال کرد. توصیف یک شی به شرح هر جزء از شی خلاصه می شود. اگر یک شی از چندین فیلد تشکیل شده باشد، هر فیلد، نوع، نام آن (مقادیر ممکن چیست) توضیح داده می شود. فیلدها همچنین می توانند از نوع پیچیده باشند و به همین ترتیب تا زمانی که شرح انواع به موارد ساده ختم شود - رشته، بولی، عدد، تاریخ... با این حال، برخی از انواع خاص ممکن است ساده باشند، مهم است که مشتریان می توانند بفهمند که چه ارزش هایی ممکن است شامل شوند.

برای مشتریان کافی است آدرس وب سرویس را بدانند که wsdl همیشه در نزدیکی آن خواهد بود که از طریق آن می توانید از روش ها و پارامترهای آنها که این وب سرویس ارائه می دهد ایده بگیرید.

مزایای این همه زنگ و سوت چیست:

  • در اکثر سیستم ها، شرح روش ها و انواع به طور خودکار اتفاق می افتد. آن ها برنامه نویس روی سرور فقط باید بگوید که این روش را می توان از طریق وب سرویس فراخوانی کرد و توضیحات wsdl به طور خودکار تولید می شود.
  • توضیحاتی که ساختار واضحی دارد برای هر مشتری صابونی قابل خواندن است. آن ها مهم نیست که وب سرویس چیست، مشتری متوجه می شود که وب سرویس چه داده هایی را دریافت می کند. با استفاده از این توضیحات، کلاینت می تواند ساختار داخلی خود را از کلاس های شی بسازد، به اصطلاح. binding" و. در نتیجه، برنامه نویسی که از وب سرویس استفاده می کند باید چیزی شبیه (شبه کد):

    NewUser:=TSoapUser.Create("Vasya","Pupkin",""admin"); soap.AddUser(NewUser);

  • اعتبار سنجی خودکار

    • اعتبار سنجی xml xml باید به خوبی شکل گرفته باشد. xml نامعتبر - بلافاصله یک خطا برای مشتری، اجازه دهید او آن را مرتب کند.
    • اعتبار سنجی طرحواره xml باید ساختار خاصی داشته باشد. xml با طرح مطابقت ندارد - بلافاصله یک خطا برای مشتری، اجازه دهید او آن را مرتب کند.
    • تأیید داده ها توسط سرور صابون انجام می شود تا انواع داده ها و محدودیت ها با توضیحات مطابقت داشته باشند.
  • مجوز و احراز هویت را می توان با استفاده از یک روش جداگانه پیاده سازی کرد. به صورت بومی یا با استفاده از مجوز http.
  • سرویس های وب می توانند هم از طریق پروتکل صابون و هم از طریق http، یعنی از طریق دریافت درخواست ها، کار کنند. یعنی اگر پارامترها داده های ساده (بدون ساختار) باشند، می توانید به سادگی دریافت معمولی www.site.com/users.asmx/GetUser?Name=Vasia یا پست را فراخوانی کنید. با این حال، این همه جا و همیشه نیست.
  • ... در ویکی پدیا ببینید

همچنین معایب زیادی وجود دارد:

  • اندازه پیام بزرگ غیر منطقی خب، در اینجا ماهیت xml به گونه‌ای است که فرمت اضافی است، هر چه تگ‌ها بیشتر باشد، اطلاعات بی‌فایده‌تر می‌شود. صابون پلاس افزونگی آن را اضافه می کند. برای سیستم های اینترانت، موضوع ترافیک کمتر از اینترنت است، بنابراین صابون برای شبکه های محلی بیشتر مورد تقاضا است، به ویژه Sharepoint یک سرویس وب صابونی دارد که می توانید با موفقیت (و برخی محدودیت ها) با آن ارتباط برقرار کنید.
  • تغییر خودکار توضیحات یک وب سرویس می تواند همه مشتریان را از بین ببرد. خوب، برای هر سیستمی اینطور است، اگر سازگاری عقب با روش های قدیمی پشتیبانی نشود، همه چیز از بین می رود ...
  • نه یک منفی، بلکه یک نقطه ضعف. همه فراخوانی های متد باید اتمی باشد. به عنوان مثال، هنگام کار با یک پایگاه داده، می توانیم یک تراکنش را شروع کنیم، چندین پرس و جو را اجرا کنیم، سپس rollback یا commit کنیم. هیچ معامله ای در صابون وجود ندارد. یک درخواست، یک جواب، گفتگو تمام شد.
  • پرداختن به توضیحاتی که در سمت سرور وجود دارد (آیا همه چیز به درستی توضیح داده شده است؟) و آنچه در مشتری وجود دارد (آنچه در اینجا برای من توضیح داده شد؟) می تواند بسیار دشوار باشد. چندین بار بود که مجبور شدم با سمت کلاینت سروکار داشته باشم و برنامه نویس سرور را متقاعد کنم که داده های او اشتباه توصیف شده است، اما او اصلاً چیزی در مورد آن نمی فهمید، زیرا تولید خودکار و نباید، این یک موضوع است. نرم افزار. و به طور طبیعی، خطا در کد روش بود که برنامه نویس آن را ندید.
  • تمرین نشان می دهد که توسعه دهندگان وب سرویس ها به طرز وحشتناکی از افرادی که از این خدمات وب استفاده می کنند فاصله دارند. در پاسخ به هر درخواستی (معتبر از خارج)، ممکن است یک خطای نامفهوم "خطای 5. همه چیز بد است" بیاید. همه چیز به وجدان توسعه دهندگان بستگی دارد :)
  • مطمئنم هنوز چیزی یادم نیست...

به عنوان مثال، یک وب سرویس باز انتشاریا وجود دارد:

  • http://86.57.245.235/TimeTable/Service.asmx - نقطه ورود، همچنین شرح متنی روش ها برای توسعه دهندگان شخص ثالث وجود دارد.
  • http://86.57.245.235/TimeTable/Service.asmx?WSDL - wsdl شرح روش ها و انواع داده های دریافتی و برگشتی.
  • http://86.57.245.235/TimeTable/Service.asmx?op=GetAirportsList - شرح یک روش خاص با نمونه ای از نوع درخواست xml و پاسخ xml.

شما می توانید به صورت دستی درخواستی مانند:

POST /TimeTable/Service.asmx HTTP/1.1 میزبان: 86.57.245.235 نوع محتوا: text/xml; charset=utf-8 Content-Length: length SOAPAction: "http://webservices.belavia.by/GetAirportsList" ru

جواب خواهد آمد:

HTTP/1.1 200 OK تاریخ: دوشنبه، 30 سپتامبر 2013 00:06:44 GMT سرور: Microsoft-IIS/6.0 X-Powered-By: ASP.NET X-AspNet-Version: 4.0.30319 Cache-Control: خصوصی، حداکثر -age=0 نوع محتوا: text/xml; charset=utf-8 Content-Length: 2940

PS قبلاً وب سرویس Aeroflot باز شده بود، اما پس از اینکه 1C پشتیبانی صابون را به 8ku اضافه کرد، گروهی از آزمایش‌کنندگان بتا 1C آن را با موفقیت نصب کردند. اکنون چیزی در آنجا تغییر کرده است (آدرس را نمی دانم، اگر علاقه دارید می توانید آن را جستجو کنید).
سلب مسئولیت ZZY. او در سطح روزمره صحبت می کرد. می توانید لگد بزنید.

دیدگاه ها