この PHP ライブラリには次のものが含まれます
また、ソース システムから Sharpspring の連絡先/リード データベースへの連絡先データの同期プロセスを実装するいくつかのサンプル/部分クラスも含まれています。これは、Sharpspring リードのローカル キャッシュと連携して、Sharpspring REST API への更新呼び出しを最小限に抑えます。
クライアント クラスはスタンドアロンで使用できますが、このライブラリはそのために作成されたものではありません。独自のパラメータを構築し、その結果を自分でデコードしたい場合は、先に進んでください。それをインスタンス化します。 call() メソッドを呼び出します。ライブラリの残りの部分は必要ありません。
Connection クラスの目的は、Sharpspring の REST API との通信について混乱しないようにすることです。次の方法でこれを支援しようとします。
(LocalLeadCache クラスについてはここでは説明しません。)
use SharpSpring RestApi Connection ;
use SharpSpring RestApi CurlClient ;
// One thing this library does not make super easy: starting. Separation of
// concerns is considered more important, so (since the actual API call was
// abstracted into CurlClient) creating a new connection takes 2 lines instead
// of 1:
$ client = new CurlClient ([ ' account_id ' => . . . , ' secret_key ' => . . . ]);
$ api = new Connection ( $ client );
// Get all leads updated after a certain time (notation in 'local' timezone,
// though there is no formal definition of what 'local' entails).
$ leads = $ api -> getLeadsDateRange ( ' 2017-01-15 10:00:00 ' );
コードは、遭遇した奇妙なものに対して例外をスローします...呼び出している特定の API/接続メソッドによって予期される配列値以外に、応答に表示される追加のプロパティを除いて。これらはデフォルトでは無視されます。彼らに遭遇することは期待されていません。これらをログに記録したい場合は、PSR-3 互換のロガー オブジェクトを 2 番目の引数として Connection コンストラクターに渡します。
Sharpspring REST API の「オブジェクト」(配列) では、カスタム フィールドはシステム名によって参照され、これはアカウントごとに異なります。より一般的なコードを記述できるようにするために、Connection オブジェクトにはカスタム プロパティからフィールド システム名へのマッピングがあります。このマッピングが (プロパティ名を独自に選択して) 設定されると、REST API 呼び出しの「オブジェクト」パラメータのカスタム プロパティ名が、対応するフィールド システム名に自動的に変換されます。
Sharpspring UI を使用して作成した靴のサイズのカスタム フィールドを持つ靴店のリードがあり、そのシステム名がshoe_size_384c1e3eacbb3 であるとします。次の 2 つの例は同等です。
$ api -> createLead ([
' firstName ' => ' Roderik ' ,
' emailAddress ' => ' [email protected] ' ,
' shoe_size_384c1e3eacbb3 ' => 12 ,
]);
$ api -> setCustomProperties ( ' lead ' , [ ' shoeSize ' => ' shoe_size_384c1e3eacbb3 ' ]);
$ api -> createLead ([
' firstName ' => ' Roderik ' ,
' emailAddress ' => ' [email protected] ' ,
' shoeSize ' => 12 ,
]);
// Note that system names will still be OK; after setCustomProperties is called,
// you can still send in [...,'shoe_size_384c1e3eacbb3' => 12, ...]. Just don't
// set values for _both_ the field name _and_ its property alias, because then
// the library does not guarantee which of the two will be used.
自動変換は、API 呼び出しパラメータの「オブジェクト」に対してのみ行われます。 API 呼び出しから返された結果は改ざんされません。 API 結果のカスタム フィールド システム名をカスタム プロパティ名に変換し直す場合は、これを明示的に行う必要があります。
$ api -> setCustomProperties ( ' lead ' , [ ' shoeSize ' => ' shoe_size_384c1e3eacbb3 ' ]);
$ leads = $ api -> getLeads ([ ' emailAddress ' => ' [email protected] ' ]);
$ lead = reset ( $ leads );
$ my_lead = $ api -> convertSystemNames ( ' lead ' , $ lead );
API の「オブジェクト」表現に配列を使用しても問題ありません。ただし、オブジェクト/クラスを使用することを好む場合もあります。 (これにより、IDE オートコンプリートが提供され、REST API が処理できないプロパティ名の大文字が間違って使用される可能性も最小限に抑えられます)。
基本クラスは ValueObject で、現時点では、すべての既知のフィールドを実装する Lead クラスがあります (Sharpspring の API ドキュメントが古い箇所についてはコメントが付いています)。
次の例は上記と同じです。
/**
* If you have custom fields, you will want to define your own subclass:
*/
class ShoeStoreLead extends Lead
{
// Define your own properties:
public $ shoeSize ;
}
$ api -> setCustomProperties ( ' lead ' , [ ' shoeSize ' => ' shoe_size_384c1e3eacbb3 ' ]);
// This is the create call from above. Note createLead() accepts ValueObjects as
// well as arrays.
$ lead = new ShoeStoreLead ();
$ lead -> firstName = ' Roderik ' ;
$ lead -> emailAddress = [email protected]';
$ lead -> shoeSize = 12 ;
$ api -> createLead ( $ lead );
// And this is the 'get' call which puts the result into a new object:
$ leads = $ api -> getLeads ([ ' emailAddress ' => ' [email protected] ' ]);
$ lead = reset ( $ leads );
$ my_lead = $ api -> convertSystemNames ( ' lead ' , $ lead );
$ my_lead_obj = new ShoeStoreLead ( $ my_lead );
明らかに、カスタム フィールドがない場合、この例ははるかに単純になります (Lead をサブクラス化したり、setCustomProperties() / ConvertSystemNames() を使用したりする必要がないため)。
上の例では、ValueObject はそのプロパティのフィールド システム名へのマッピングについて何も知りません。 Connection オブジェクトは作成/更新操作でこれを処理します。「get」操作の後は、オブジェクトを構築する前にそれらを明示的にカスタム プロパティ名に変換し直す必要があります。
別の方法もあります。Connection の代わりに ValueObject でマッピングを設定することもできます。
$ mapping = [ ' shoeSize ' => ' shoe_size_384c1e3eacbb3 ' ];
// $api->setCustomProperties('lead', $mapping) is not called here.
// For create:
$ lead = new ShoeStoreLead ([], $ mapping );
$ lead -> firstName = ' Roderik ' ;
$ lead -> emailAddress = [email protected]';
$ lead -> shoeSize = 12 ;
$ api -> createLead ( $ lead );
// Note you could also add all the properties in the first argument of the
// constructor, instead of setting them individually - although that more or
// less defeats the purpose of using a ValueObject in the first place. Setting
// 'shoeSize' works just as well as 'shoe_size_384c1e3eacbb3', in that first
// argument. Just don't set values for _both_ the field name _and_ its property
// alias, because then the library does not guarantee which of the two will be
// used.
// For 'get':
$ leads = $ api -> getLeads ([ ' emailAddress ' => ' [email protected] ' ]);
$ lead = reset ( $ leads );
$ my_lead_obj = new ShoeStoreLead ( $ my_lead , $ mapping );
したがって、カスタム フィールドを持つ ValueObject の場合、接続のマッピングを設定するか、ValueObject に設定するオプションがあります。後者には、REST API から取得したデータがコンストラクター内で自動的に変換されるという利点がありますが、オブジェクトを構築するたびにマッピングを設定する必要があるという欠点があります。
別の方法もあります。次のように、オブジェクト内のマッピングをハードコーディングします。
// Override the parent's (empty) property mapping variable:
protected $_customProperties = ['shoeSize' => 'shoe_size_384c1e3eacbb3'];
...または、カスタム ValueObject サブクラスのコンストラクターを作成して設定します (または、どこかから派生させます)。それはおそらく、あなた自身の状況に固有のコードになるでしょう。
好みのアプローチを選択してください。
Sharpspring REST API の最も奇妙な動作は文書化されているか、このライブラリによって部分的に緩和/隠蔽されています。ただし、API に基づいて本格的な作業を行う場合は、少なくとも知っておくべきことがいくつかあり、これらを考慮する必要があるかどうかを判断する必要があります。
標準以外の文字を含む値 (おおよそ: htmlspecialchars() によってエンコードされる文字) は、REST API を介して挿入されたか、UI を介して入力されたかに応じて、Sharpspring に異なる方法で格納されます。 (UI に関しては、標準フィールドとカスタム フィールドでも異なります。) 「<」はさらに奇妙で、二重エンコードされて保存されることがあります。悲惨な詳細はencoding.mdにあります。このライブラリがこの動作を軽減できる唯一の方法は、必要かどうかに関係なく、CurlClient がフィールドを常に HTML デコードすることです。 HTML デコードは透過的に行われるため、この動作は見られない可能性がありますが、本格的なアプリケーションでは、これが問題かどうかを検討する必要があります。
updateLead 呼び出しでは、(少なくとも) 変更された電子メール アドレスとともに既存の「id」値を送信することで、既存のリードの電子メール アドレスを変更できます。ただし、変更された電子メールが別の既存のリードですでに使用されている場合、API は通知なく更新を破棄しますが、それでも成功を報告します。これは、電子メール アドレスが必ずしも一意ではない既存の連絡先データベースを Sharpspring にミラーリングしている場合に潜在的な問題になります。更新が成功したかどうかを再確認する必要があります。 (そのようなコードの一例は、SharpspringSyncJob::finish() にあります。)
(これらのバグが修正されたという報告を歓迎します。修正される可能性があります。「警告」を参照してください。)
Sharpspring は、発表やドキュメント/変更ログを作成せずに API の動作を変更することがあるようです (私の知る限りでは、どちらも変更しません)。また、ログイン後に見つかるオンライン API ドキュメントに記載されている API バージョンを上げなくても、API の動作を変更することがあります。彼らの顧客サイト。
このことからわかることは、アプリケーション開発者として、Sharpspring があなたとの「暗黙の契約」を破らないとは信頼できないため、アプリケーションを常にテストする必要があるということのようです。なぜなら、Sharpspring は、アプリケーション開発者と「暗黙の契約」を結んでいるとは明らかに感じていないからです。
(このライブラリを半年かけて開発していたときに、この点についていくつかの疑問を感じましたが、これは getLeadsDateRange 呼び出しの動作の変化に基づいています ('timestamp' パラメーターを に設定した場合) "update") - パラメーターと出力の日付の形式と出力の内容の両方が変更されます。これにより、SharpspringSyncJob クラスを使用する運用システムで即時に影響が発生します (エラーが報告されます)。緊急パッチが適用される予定です。公開されている API バージョンはまだ 1.117 であり、少なくとも 2016 年 11 月以降のものです。
この動作の変更は、私が報告した不一致が原因である可能性があります (短い電子メールのやり取りがあり、その結果、API で発生した問題のリストを送信しました)。彼らが不一致を修正しているのはうれしいですが、不足しているのは応答、変更ログ、または API バージョンの変更は、依然として上記の要点につながります。もちろん、これが将来的に変更され、この警告が削除されることを期待していますが、現時点では本当に適切だと思われます。)
ああ、見てください! https://help.sharpspring.com/hc/en-us/articles/115001069228-Open-API-Overview には、「v1」 API と「v1.2」 API があることが記載されています。 2 つ目は日付入力を UTC として受け入れているようです (v1 API は 2017 年 7 月 26 日頃までそうでした)。出力日付の形式については言及されていないため (これも v1 で変更されました)、テストが必要です。このライブラリは現在 API v1 のみを実行するため、拡張する必要があります。私の最終候補リストには入っていないので、PR (または有償の任務 ;)) を歓迎します。
このコードは、Leads と ListMembers でテストされています。さらに多くの API 呼び出しが存在しますが、そのすべてが広範囲にテストされているわけではなく、一部が欠落しています。新しい呼び出しを追加するのは、大した作業ではないことを願っています。プルリクエストは歓迎されます。
PR を送信するか、私に連絡してください。
「ビルド プロセス」 (上部のアイコンを参照。同様の成功/失敗メッセージが PR に表示されます) は、コーディング標準を PHP5.6 / PSR2 に対してチェックするだけです。これは、Sharpspring をラップするコードの薄い層にすぎないため、まだ単体テストはありません。テストが必要だと思うかどうか、またその理由を教えてください。 (ライブの Sharpspring APIに対する完全なテストスイートがあれば当然良いでしょうが、それは別の問題であるか、少なくともそれらとのさらなる調整が必要だと思います...)
私はオープンソース ソフトウェアを世界に貢献するのが好きで、文書化されていない半クローズドなシステムをオープンにするのが好きです。これが役立つ場合、または貢献がある場合は、お知らせください。統合作業が必要な場合は、私に連絡してください。 (私は他のいくつかのシステムの経験があります。)
このライブラリは MIT ライセンスに基づいてライセンスされています。詳細については、LICENSE.md ファイルを参照してください。