CopyrightIBMCorporation2006TrademarksBuildingPHP-basedUIsforIBMLotusDominoPage1of14BuildingPHP-basedUIsforIBMLotusDominoAndreiKouvchinnikovMay09,2006DiscoverhowyoucaninteractwithLotusDominodatabasesfromWebapplicationscreatedinthePHPprogramminglanguage.
LearnhowtoaccessDominoapplicationsfromPHPpagesusingaCOMobject,theLotusNotesAPI,andXML.
Inthisarticle,youlearnhowtointeractwithIBMLotusDominodatabasesfromWebapplicationscreatedwiththePHPprogramminglanguage.
YoualsolearnhowtoaccessDominoapplicationsfromPHPpagesusingaCOMobject,theIBMLotusNotesapplicationprogramminginterface(API),andXML.
CodeexamplesforeachmethodareincludedintheDownloadssection.
TheXMLmethodalsohasadownloadableexampleapplicationwithasimpleWebinterfacetoanIBMLotusDominomaildatabase(seefigure1).
Figure1.
ExampleofaPHPuserinterfacetoamaildatabasePHPisapowerfulembeddedscriptinglanguage.
ItisfreetouseandpopularfordevelopingdynamicWebapplications.
PHPcodeisn'tcompiled;rather,it'sinterpretedatruntime.
MuchofitssyntaxisborrowedfromtheC,Java,andPerlprogramminglanguages.
YoucanaddPHPasaCommonGatewayInterface(CGI)enginetomostWebservers.
ItevenworksintheMicrosoftWindowsandLinuxoperatingsystems.
Inaddition,morethan50percentofWebhostingcompanieshavePHP-enabledservers.
WithsuchwidespreadPHPtechnology,yousimplycannotaffordtoremainunfamiliarwithit.
WorkingwithPHPYouincludePHPcodeinWebpageswiththehelpofspecialtags.
AllPHPcodebeginswiththetag:developerWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage2of14TheWebserverinterpretsthissimpleexampleandtranslatesittofollowingHTMLoutput:HelloWorld!
PHPWebpagescaninteractwithDominodatabasesinseveralways.
ThechoiceofintegrationmethoddependsonwhichoperatingsystemyouusetorunPHP,thesecurityrestrictionsinplacebetweenPHPandyourDominoservers,andwhatyouareallowedtoinstallonthePHPserver.
Themethodsdescribedinthisarticleare:COMobjectsTheNotesAPIXMLthroughtheWebRunningPHPcodeofflineAlthoughPHPisprimarilyintendedtorunonaWebserverandisnotforstandaloneapplications,youcanrunitfromthecommandlineasashellscriptingtoolsimilartoMicrosoftVisualBasicScriptingEdition(VBScript).
ThisfeaturecanbeusefulforofflinetestingbeforeputtingthefilesontheWebserver.
AccessingLotusDominoThreemethodsareavailableforaccessingaDominodatabase:throughCOMobjects,throughtheNotesAPI,andthroughXML.
AccessLotusDominousingDominoCOMobjectsTheeasiestandmostfast-forwardmethodofaccessinginformationstoredinDominodatabasesisthroughDominoCOMobjects.
UsingCOMfromPHPisn'tmuchmoredifficultthandoingsofromLotusScript.
Thefollowingcodeexampleshowshowtoprintthefieldvaluesofallthedocumentsinaview.
Initialize();//ShowthenameofthecurrentNotesuserprint"Currentuser:".
$session->CommonUserName.
"\n\n";//Getdatabasehandle$db=$session->getDatabase("","mailtest.
nsf");//Getviewhandleusingpreviouslyreceiveddatabasehandle.
//Notethatthereservedcharacterintheviewnamemustbe\-escaped$view=$db->getView("(\$Drafts)");ibm.
com/developerWorks/developerWorksBuildingPHP-basedUIsforIBMLotusDominoPage3of14//Getfirstdocumentinviewusingpreviouslyreceivedviewhandle$doc=$view->getFirstDocument();//Loopuntilalldocumentsinviewareprocessedwhile(is_object($doc)){//Gethandletoafieldcalled"Subject"$field=$doc->GetFirstItem("Subject");//Gettextvalueofthefield$fieldvalue=$field->text;//Showthevalueofthefieldprint"Subject:".
$fieldvalue.
"\n";//Getnextdocumentintheview$doc=$view->getNextDocument($doc);}//Releasethesessionobject$session=null;>Figure2showstheoutputfromrunningthisCOMobjectfromthecommandline.
Figure2.
ResultofrunningCOMobjectcodeatacommandpromptUsingCOMobjectsiseasy,buttherearesomedisadvantagesthatmakeCOMratherlimited.
ThemaindisadvantageisthatyoumusthaveLotusNotesclientsoftwareinstalledonthePHPserver.
Ifyou'reusingaWebhostingcompanyforyourPHPapplications,thereisn'tmuchyoucandotoconvincethehostingcompanytoinstallaNotesclientjustforpurposesofyourPHPWebsite.
IfyouhaveyourownPHPserverorperhapsPHPandDominoserversonthesamecomputer,youshouldhavenoproblemssettingupCOMaccesstotheDominoserver.
AnotherissuethatlimitsCOMuseisthatCOMobjectsaresupportedonlyontheWindowsplatform.
ConsideringthatmostPHPserversrunontheLinuxplatform,thisrequirementconsiderablyreducesthenumberofavailableserversthatcanhostyourCOMsolution,evenifyouhavefulladministrativecontrolforthoseservers.
AccessLotusDominothroughanAPIAnalternativetoCOMaccessistousetheLotusNotes/DominoCAPI.
Theoretically,youcanusethissolutiononoperatingsystemsotherthanWindows.
WerecommendthatonlydeveloperswhohavealotofexperienceinC/C++programminguseit(ifyouhaveareasonfornotusingaCOMinterfaceorXML).
ThefunctionalityprovidedinthesampleAPIsolutionislimited,andyoumustbasicallywriteyourowncodeintheCprogramminglanguagetoaccomplishmosttasks.
developerWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage4of14ThesamplelibraryprovidesagoodexampleforcreatingPHPextensions.
Itcomesonlyassourcecode,andyoumusthavetheVisualCcompilerandtheDominoCAPItoolkittocompilethecode.
Foryourconvenience,we'vecompiledthesourcecodeintoaDLLfileandincludeditintheDownloadssection.
YoucanactivatetheNotesextensionbyaddingthefollowinglinetothephp.
iniconfigurationfile:extension=php5_notes.
dllThefollowingcodeexampleshowshowtousethistechniqueafteryouproducetherequiredDLL.
Figure3showstheoutputfromrunningtheAPIcodefromthecommandline.
Figure3.
OutputoftheAPIcodeAccessLotusDominousingXMLUsingXMLtointeractwithDominodatabasesisthemostcompatiblesolution.
Itdoesn'trequireanyspecialadjustmentsorinstallationsonthePHPWebserver,anditworksonalloperatingsystems.
Inouropinion,it'sthebestapproachinmostcases.
IntheXMLsolutioninthisarticle,youusetechniquesthataremostlikelytoworkinthemajorityofconfigurations.
Asanexample,youcreateaPHPinterfacetoastandardDominomaildatabase.
TheonlymodificationmadeintheDominoenvironmentisaLotusScriptagentusedtoviewfieldsfromthemaildocuments.
YouusethesameagenttoparsetheXMLandtocreateandsendmail.
ibm.
com/developerWorks/developerWorksBuildingPHP-basedUIsforIBMLotusDominoPage5of14ToviewtheInboxfolderfromthemaildatabase,completethesesteps:1.
AsktheuserforhisorherNotesusernameandpassword.
2.
SendaloginrequesttotheDominodatabaseusingtheusernameandpasswordprovided(seefigure4).
Figure4.
LoginscreeninthePHPsampleapplication3.
Fromtheloginresponse,getasessioncookie.
(YouneedthiscookieforsubsequentrequeststotheDominodatabase.
)4.
MakearequesttotheDominoserverfortheXMLsourceoftheInboxfolder,usingtheReadViewEntriesURLcommand.
ThiscommandreturnsthecontentoftheviewpresentedinXMLforminsteadofreturningHTML.
YoutellDominoyouridentitybyappendingasessioncookietotherequestheaders.
5.
OnthereceivedXML-formattedviewcontent,usePHP'sXMLparsertofinddocumentsandfields.
6.
WhentheXMLparserhasprocessedthewholedocument,constructtheHTMLcode,andprinttothebrowser.
Tomakeamailmessageaclickablelink,usetheUNIDattributeofeachdocumentnode.
ToaccessDominodatabases,youneedfunctionalitybothtogetaWebpagefromtheDominoserverandtoparsetheXML.
Youmustalsoassumethefollowingforpurposesofthedemoapplication:TheDominoserverisversion6orlater;otherwise,youcan'tuseLotusScript'sXML-parsingfunctionality.
(ThisLotusScriptagentisdiscussedinmoredetaillater.
)ThePHPWebserverallowsoutgoingWebrequests.
TheDominoserverisaccessiblefromthePHPWebserverbyeithertheInternetoranintranet.
Note:Ifyoucan'taccesstheDominoserverfromtheInternet,youmayneedtoadjustyourfirewallconfigurationtoallowtrafficfromthePHPserver.
PHPfunctionsforreadingWeb-basedDominofilesPHPhasseveralfunctionsforretrievingWeb-basedcontent.
ThesefunctionswereincludedinPHPfromtheinception,butadministratorshaven'talwaysactivatedthem.
ThefollowingfunctionscanretrieveafilefromtheWeb:developerWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage6of14file_get_contents().
Thisfunctioniseasytouse,anditsupportsboththeGETandPOSTrequesttypes.
Withfile_get_contents(),yougetthewholeWebfileatonceasastring.
fopen().
ThismethodreadstheWebfileinchunks.
file().
ThismethodreadsthewholeWebfileandseparatesthefile'scontentlinebyline.
It'sakindofcross-overbetweenfile_get_contents()andfopen().
fsockopen().
ThisfunctionhasthegreatestchanceofbeingactivatedonthehostingWebserver.
Themaindifferencebetweenthisandotherfunctionsisthatwithfsockopen(),youmustcreatethewholeWebrequestbyyourselfinsteadofsettingdifferentparameters.
CURL.
TheClientURLLibrary(CURL)hasthemostadvancedfunctionality.
UsingCURL,youcanconnecttoandcommunicatewithmanydifferenttypesofserverswithmanydifferenttypesofprotocols.
CURLcurrentlysupportsHTTP,HTTPS,FTP,Gopher,Telnet,DICT,File,andLDAP.
Italsosupportsproxies,cookies,andauthentication.
Unfortunately,CURLisoftendisabledbyWebhostingcompanies.
Note:Intheexampleapplicationinthisarticle,youusethefile_get_contents()functionexclusively.
ObtainingtheDominosessioncookieisanimportantpartoftheprocess,andyoucanusethesamecodeinotherDomino-relatedapplications.
Forexample,youcanretrieveacookieforloggingintotheIBMLotusSametimeserverusingSTLinks.
YougetthesessioncookiebysendingaPOSTrequesttotheDominoserver.
Inthatrequest,youincludeyourusernameandpassword.
TheresponsefromtheservercontainsacookiethatyouuseinsubsequentrequeststotheDominoserver.
Byincludingasessioncookie,theDominoserverthinksthatyourscriptisactuallyahumanuserwhorecentlyloggedinandisnowaccessingthedatabase.
YouusethePOSTmethodinsteadoftheGETmethodbecauseURLsoftheGETmethodareloggedintheDominolog,andanyonewhoaccessesthelogcanseetheusernameandpasswordinplaintext.
WiththePOSTmethod,usernamesandpasswordsaren'tpartoftheURL;therefore,theyaren'tvisibleinregularlogs.
YoucanfindtheDominosessioncookieintheSet-Cookieresponseheader.
ThesessioncookieiscalledeitherDomAuthSessIdorLtpaToken.
YouusethenameLtpaTokenwhentheDominoserverisconfiguredforsinglesign-on(SSO).
Youdon'tactuallycarewhatthecookienameis;yousimplysavethewholecookiestring.
Thefollowingcodeexampleshowshowtoretrievethecookie.
$req="username=john+doe&password=john123";$opts=array("http"=>array("method"=>"POST","content"=>$req,"header"=>"Accept-language:en\r\n".
"User-Agent:Mozilla/4.
0(compatible;MSIE6.
0;WindowsNT5.
1)\r\n"));$context=stream_context_create($opts);if(!
($fp=fopen("http://server.
com/maildb.
nsflogin","r",false,$context))){ibm.
com/developerWorks/developerWorksBuildingPHP-basedUIsforIBMLotusDominoPage7of14die("CouldnotopenloginURL");}$meta=stream_get_meta_data($fp);for($j=0;isset($meta["wrapper_data"][$j]);$j++){if(strstr(strtolower($meta["wrapper_data"][$j]),'set-cookie')){$cookie=substr($meta["wrapper_data"][$j],12);break;}}fclose($fp);$_SESSION["DominoCookie"]=$cookie;Inthecodeline$req="username=john+doe&password=john123",youprovideavalidusernameandpasswordtobeusedforloggingintotheDominoserver.
Then,yousetupadditionaloptions,suchasthePOSTmethodtypeandotherheaders.
Afterthat,youapplyyouradditionaloptionstotheoutgoingHTTPrequest:fopen("http://server.
com/mydb.
nsflogin","r",false,$context)FromtheresponseyoureceivefromtheDominoserver,yougetalltheheadersusingthestream_get_meta_data($fp)functionandloopthroughtheheadersuntilyoufindtheonethatcontainstheSet-Cookiestring.
Afterthat,yousavethecookiebystoringitinsideasessionvariable:$_SESSION["DominoCookie"]=$cookie$_SESSIONholdsthecookievalueuntilyouclosetheWebbrowser.
Now,youapplythecookietoyournextrequest,whichretrievestheInboxview/folderfromaDominomaildatabase.
$opts=array('http'=>array('method'=>"GET",'header'=>"Accept-language:en\r\n".
"User-Agent:Mozilla/4.
0(compatible;MSIE6.
0;WindowsNT5.
1)\r\n".
"Cookie:".
$_SESSION["DominoCookie"].
"\r\n"));$context=stream_context_create($opts);$xml=file_get_contents("http://server.
com/maildb.
nsf/(\$Inbox)ReadViewEntries",false,$context);Thistime,youusetheGETmethodtodownloadaWebpageinsteadofthePOSTmethod.
Thismethodisspecifiedwiththe'method'=>"GET"lineintheHTTPoptionsarray.
Insteadofreadingonlyheaders,youreadthewholeresponseusingthefile_get_contents(URL,false,context)function.
TheresultofthisoperationisalongXMLstringcontainingallthecolumnsfromtheInboxview.
Youappendthesessioncookietotheheaderwith:"Cookie:".
$_SESSION["DominoCookie"].
"\r\n"developerWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage8of14AfteryoureceivetheXMLdata,youcanprocessitinthePHPXMLparser.
Then,youcreateyourownuserinterfacefortheInboxview.
PHPfunctionsforprocessingXMLInPHP,justasintheLotusScriptandJavaprogramminglanguages,therearetwowaysofprocessingXMLcode:theSimpleAPIforXML(SAX)andtheDocumentObjectModel(DOM).
SAXisanevent-basedprogrammingmodel,andit'sincludedandenabledbydefaultinmostPHPWebservers.
TheDOMextensionmustbeactivatedbytheWebserver'sadministrator.
AlthoughDOMismucheasiertoprogramwith,intheseexamples,youusetheSAXparserbecauseyouwanttoachievemaximumcompatibilitywithmostPHPconfigurations.
TechniquessimilartoprocessingDominoviewscan--withsmallmodifications--beusedforprocessingotherXMLsources,suchasRSSfeedsandevenWebservices.
ThefollowingcodeexampleshowstheXMLsourceoftheInboxviewcontainingonedocument.
00DonaldDuck17820060402T205929,52+0220060402T205929,52+028230seenMickeyAsyoucansee,documentsintheXMLsourcearepresentedwiththetag,andcolumns(fields)arepresentedwithtags.
Thedocument'sUniversalIDisavailableasanattributeofthenode.
ibm.
com/developerWorks/developerWorksBuildingPHP-basedUIsforIBMLotusDominoPage9of14Allyouneedtodoisdetermineawaytoprogrammaticallyfindthevaluesbetweenthosetagstogetallthedatayouneed.
Soundseasy,anditiseasytoaccomplish,too.
First,initiatetheXMLparserobjectusingthexml_parser_createfunction:$xml_parser=xml_parser_create();Then,setcallbackfunctions,whichareresponsibleforhandlingthestartandendofXMLelements.
Thesefunctionsareidentifiedtotheprocessorthroughtheuseofthexml_set_element_handlerandxml_set_character_data_handlerfunctions.
Eachfunctionacceptstheparserhandleandthenamesofthecallbackfunctions:xml_set_element_handler($xml_parser,"startElement","endElement");xml_set_character_data_handler($xml_parser,"textData");YoumustaddthestartElement,endElement,andtextDatafunctionstoyourPHPcode:functionstartElement($parser,$name,$attributes){switch($name){case"VIEWENTRY":$main="VIEWENTRY";if($attributes["UNID"]!
=""){$current_doc=$attributes["UNID"];$unids[$doc_counter]=$current_doc;}break;case"ENTRYDATA":$main="ENTRYDATA";if($attributes["COLUMNNUMBER"]!
=""){$current_column=$attributes["COLUMNNUMBER"];}break;case"DATETIME":$main="DATETIME";break;default:break;}}functionendElement($parser,$name){if($name=="VIEWENTRY"){$doc_counter++;//increasedocumentcounterby1}$current_column="";}functiontextData($parser,$data){switch($main){case"ENTRYDATA":if(isset($doc_coll[$current_doc][$main])){$doc_coll[$current_doc][$main][$current_column].
="$data";}else{$doc_coll[$current_doc][$main][$current_column]="$data";}break;case"DATETIME":if(isset($doc_coll[$current_doc][$main])){$doc_coll[$current_doc][$main].
="$data";}else{$doc_coll[$current_doc][$main]="$data";developerWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage10of14}break;case"VIEWENTRY":break;}}So,let'sseehowitworks.
WhentheXMLparsergoesthroughtheXMLsourceandfindsthatanewelementisstarted,ittriggersthestartElementfunction,whichyouspecifiedasacallbackfunction.
Inthiscase,suchastartingelementnameis.
Nowyouknowthatthecurrentelementbeingprocessedisanewcolumn,soyoucansetthe$current_columnvariabletothenumberofthecolumn.
Inthiscase,columnsrepresentfields:case"ENTRYDATA":$main="ENTRYDATA";if($attributes["COLUMNNUMBER"]!
=""){$current_column=$attributes["COLUMNNUMBER"];}break;Afterthat,theparserfindsthetextinsidethenodeandsendsittothetextDatafunctionthatyouspecifiedasacallbackfunction.
Thepurposeofthisfunctionistoallowyoutopopulateanarraywithvaluesinsidethenode:switch($main){case"ENTRYDATA":if(isset($doc_coll[$current_doc][$main])){$doc_coll[$current_doc][$main][$current_column].
="$data";}else{$doc_coll[$current_doc][$main][$current_column]="$data";}break;UsingtheXMLsourceexample,the$doc_coll[$current_doc][$main][$current_column]="$data"codelineis:$doc_coll["38B16601EC8B42BAC12571440068335C"]["ENTRYDATA"]["8"]="seenMickey"ThismeansthattheeighthcolumnintheInboxviewforthedocumentwithUniversalID38B16601EC8B42BAC12571440068335Cis"seenMickey",whichhappenstobethesubjectofthemailmessage.
TheXMLparseris"smart"andknowsthatifanelementisstarted,itmustbefinishedsomewhere.
So,whenitfindstheendoftheelement,itsignalsyoubytriggeringtheendElementfunction(that'sright:thesamefunctionnameyouspecifiedasyoursecondcallbackfunction).
Inthatfunction,youresetthecolumnnumberbecauseitisn'tneededanymore.
Youalsocheckwhetherthedocumentcountermustbeincreased.
Youusethe$doc_countervariableasacounterforthearraythatstoresUniversalIDs.
YoumuststoreUniversalIDsmainlyforthepurposeofaddinglinkstothemaildocuments.
WhenyouknowthattheVIEWENTRYelementhasended,itmeansthatanewUniversalIDiscomingnext,andibm.
com/developerWorks/developerWorksBuildingPHP-basedUIsforIBMLotusDominoPage11of14youhadbetterincreasethecurrentarraynumberby1tokeepthe$doc_colland$unidsarraysintact:if($name=="VIEWENTRY"){$doc_counter++;}$current_column="";Ifyoudownloadthesampleapplicationandrunitonyourownserver,yourversionoftheDominomaildatabasemayhavedifferentplacementofcolumnsinthemailviews.
Ifso,youmustadjustthecolumnnumbersinthePHPcode(docfunctions.
php).
ThesamplePHPapplicationandtheLotusScriptagentThissectionisaboutaDominoagentcalledProcessDocWebAction,whichisincludedaspartofthesampleapplicationyoucandownloadwiththisarticle.
TheagentisprogrammedinLotusScriptandusestheDOMtoparseincomingXMLrequests.
BecauseitusesthenewXMLscriptclasses,youcanusetheapplicationonDominorelease6andrelease7servers,butnotonrelease5servers.
TherequeststhatthisagenthandlesareinitiatedfromthesamplePHPapplicationandcanbeofthefollowingtypes:CreateandsendamailmessageSaveanexistingmaildocumentSaveanewmaildocumentasdraftRequestinformationaboutthelocationofauser'sfileAdummyPingrequesttomakesurethatauserisstillloggedinTodeploytheagent,completethesesteps:1.
Copyallthetextfromthexmlagent.
lssfile.
2.
Createanewagentinadatabaseofyourchoice.
3.
Setthepropertiesoftheagentto"RunasWebuser"andthetargettoNone.
4.
Pastethecopiedcodeintothisnewagent.
5.
NametheagentProcessDocWebAction,andthensaveit.
6.
InthePHPfile(dominomail.
php),pointtotheURLlocationofthedatabaseinwhichtheagentresides.
OneofourmainprioritiesduringthecreationofthePHPsampleapplicationwastoensurethatitworkedonallstandardmaildatabaseswithoutdesignmodifications.
That'swhythisapplicationdoesn'trequireanychangestothemaildatabasedesign.
YoucanplacetheagentforprocessingtheXMLoutsidetheuser'smaildatabase,andthesameagentcanbeusedforservingallusers.
Whenauserauthenticatesforthefirsttime,thePHPapplication,afterretrievingthesessioncookie,asksthisagentforthelocationoftheuser'smailfile.
Theagentknowswhotheinvokeroftheagentisbecausetheagentisrunningwiththe"RunasWebuser"propertyactivated.
AfterdeveloperWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage12of14thisinitialrequest,thepathtotheuser'smaildatabaseissavedforre-useuntiltheuserclosestheWebbrowserorthesessionexpires.
AuserisalwaysauthenticatedusingrealDominoauthentication.
TheusercannotaccessanyresourcesheorshecannotaccessusingaWebbrowserclient,eveniftheusercouldmodifythePHPsourcecodeontheWebserver.
ConclusionIfyou'reaDominodeveloperoradministratorandyourDominoserverisn'taccessiblefromtheInternet,youcanstillgiveusersawaytoaccessdatastoredinDominodatabasesandallowthemtoreadandwriteemailmessages.
UsingtheXMLtechniquesdescribedinthisarticleandappliedinthesampleapplication,youcaneasilyimplementDominoauthenticationinyourownPHPapplicationstoverifyloginsagainsttheDominoDirectory.
Thereisnooverridingofauser'saccessrightsintheWeb-basedXMLsolution;theuserisusinghisorherowncredentialsineachoperation.
Thisensuresthatuserscannotaccessunauthorizeddata.
Tofurtherincreasesecurity,youcanimplementloggingoffailedloginattempts.
ibm.
com/developerWorks/developerWorksBuildingPHP-basedUIsforIBMLotusDominoPage13of14DownloadableresourcesDescriptionNameSizeSourcecodeofPHPapplicationphp_app_sample.
zip10KBLotusScriptagentusedforprocessingXMLxmlagent.
zip2KBCompiledversionofNotesAPIextensionphp_notes_dll.
zip21KBdeveloperWorksibm.
com/developerWorks/BuildingPHP-basedUIsforIBMLotusDominoPage14of14RelatedtopicsdeveloperWorksarticle,"ReadingandwritingtheXMLDOMwithPHP"PHPWebsitePHP:XMLParserFunctionsTryalivedemoofthePHPinterfacedemotoaDominomaildatabase.
DownloadatrialversionofLotusNotes7fromdeveloperWorks.
DownloadatrialversionofLotusDomino7fromdeveloperWorks.
DownloadthesourcecodeoftheNotesAPIextensionforPHPfromthePHPExtensionCommunityLibrary(PECL)site.
CopyrightIBMCorporation2006(www.
ibm.
com/legal/copytrade.
shtml)Trademarks(www.
ibm.
com/developerworks/ibm/trademarks/)
云步云怎么样?云步云是创建于2021年的品牌,主要从事出售香港vps、美国VPS、日本VPS、香港独立服务器、香港站群服务器等,机房有香港、美国、日本东京等机房,目前在售VPS线路有CN2+BGP、CN2 GIA,香港的线路也是CN2直连大陆,该公司旗下产品均采用KVM虚拟化架构。目前,云步云提供香港安畅、沙田、大浦、葵湾、将军澳、新世界等CN2机房云服务器,2核2G5M仅72.5元/月起。点击进...
mineserver怎么样?mineserver是一家国人商家,主要提供香港CN2 KVM VPS、香港CMI KVM VPS、日本CN2 KVM VPS、洛杉矶cn2 gia端口转发等服务,云服务器网(yuntue.com)介绍过几次,最近比较活跃。现在新推出了3款特价KVM VPS,性价比高,香港CMI/洛杉矶GIA VPS,2核/2GB内存/20GB NVME/3.5TB流量/200Mbps...
之前分享过很多次CloudCone的信息,主要是VPS主机,其实商家也提供独立服务器租用,同样在洛杉矶MC机房,分为两种线路:普通优化线路及CN2 GIA,今天来分享下商家的CN2 GIA线路独立服务器产品,提供15-100Mbps带宽,不限制流量,可购买额外的DDoS高防IP,最低每月82美元起,支持使用PayPal或者支付宝等付款方式。下面分享几款洛杉矶CN2 GIA线路独立服务器配置信息。配...
file_get_contents为你推荐
"2016年中文图书第27期新书通报",,,,,思科flash支持ipad重庆网通中国联通重庆分公司的公司简介ipadwifiipad的wifi打不开怎么办?ipadwifiipad插卡版和wifi版有什么区别,价格差的多么?ipad上网为什么ipad网速特别慢x-routerx-arcsinx的等价无穷小是什么?google中国地图谷歌退出中国,地图要是关了就太可惜了!手机谷歌地图还能用吗?杀毒软件免费下载2013排行榜现在有那些杀毒软件是好用又免费的
双线vps lamp bluehost 12u机柜尺寸 lamp配置 主机合租 京东商城双十一活动 免费申请个人网站 免费网页空间 德隆中文网 酸酸乳 登陆qq空间 国外免费云空间 黑科云 好看的空间 优惠服务器 服务器是什么意思 ddos攻击器下载 灵动:鬼影实录 灵动:鬼影实录2 更多