Ich hatte die Gelegenheit, eine Funktion zum Austausch von Nachrichten zwischen einem in Ruby geschriebenen System und LINE, einem allgemeinen Benutzer, zu entwickeln, damit ich das damals gewonnene Wissen weitergeben kann.
Ich habe auch eine Demo einer funktionierenden Anwendung mit Rails erstellt. Ausführliche Informationen zur Implementierung finden Sie unter hier. Ich denke, dass der Inhalt des Artikels reibungslos eingehen wird, wenn Sie fragen.
Ein Systemadministrator (im Folgenden als "Administrator" bezeichnet) und ein allgemeiner Benutzer (im Folgenden als "Benutzer" bezeichnet) erstellen eine Funktion zum Austausch von Textnachrichten über LINE. Da das System die LINE-Informationen des Benutzers kennen muss, um tatsächlich kommunizieren zu können, implementieren wir auch die LINE-Anmeldung im Browser.
Wenn der Benutzer nach dem Verknüpfen der LINE-Informationen des Benutzers eine Nachricht an das mit dem Administrator verknüpfte offizielle LINE-Konto sendet, wird die Nachricht von Webhook an das System gesendet und von dort in der Datenbank gespeichert. Das Bild entspricht in etwa der Abbildung unten.
Der Administrator kann auch LINE-Nachrichten über das System an Benutzer senden. Wenn Sie einen Text vom System senden, können Sie über das Programm eine Nachricht vom offiziellen LINE-Konto des Administrators an den Zielbenutzer senden. Nach dem Senden wird die Nachricht in der Datenbank gespeichert. Das Bild ist wie folgt.
Wenn der Administrator keinen LINE-API-Kanal hat, ist es nicht möglich, über LINE mit Benutzern zu kommunizieren. Erstellen Sie ihn daher. Machen wir es von LINE Developer Console. Der Kanal, den Sie dieses Mal erstellen müssen
Es gibt zwei.
Die Messaging-API fungiert als offizielles LINE-Konto. Als Einschränkung setzen wir den ** Antwortmodus auf "Bot" **. Im Chat-Modus kann ich vom offiziellen LINE-Account-Manager aus kommunizieren, aber keine Webhooks empfangen. Daher muss es im Bot-Modus verwendet werden, da das Problem besteht, dass das System kein Protokoll der Interaktion führen kann. Klicken Sie hier, um Details zum Erstellen zu erhalten (https://developers.line.biz/ja/docs/messaging-api/getting-started/#%E3%83%81%E3%83%A3%E3%83%8D% E3% 83% AB% E3% 81% AE% E4% BD% 9C% E6% 88% 90) Bitte. LINE Login ist buchstäblich ein Kanal für die Verwendung von LINE Login.
Erstellen Sie nach dem Erstellen die Daten in der Admins-Tabelle der Datenbank. Ursprünglich denke ich, dass es gut ist, sich vom Bildschirm aus zu registrieren, aber es ist dazu gedacht, es seitlich zu tragen und direkt von der Konsole aus zu stecken (wenn Sie es mit dem Produktionscode in die Datenbank stellen, wird empfohlen, es aus Sicherheitsgründen verschlüsselt zu platzieren. Machen)
create_table "admins", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8mb4", force: :cascade do |t|
t.integer "line_messaging_id", null: false #Messaging-API "Kanal-ID"
t.string "line_messaging_secret", null: false #Messaging-API "Channel Secret"
t.string "line_messaging_token", null: false #Messaging-API "Channel Access Token"
t.integer "line_login_id", null: false #"Channel ID" von LINE Login
t.string "line_login_secret", null: false #LINE Login "Channel Secret"
t.datetime "created_at", precision: 6, null: false
t.datetime "updated_at", precision: 6, null: false
end
Das nächste Mal muss ich einige URLs auf der Konsolenseite von LINE festlegen, damit ich mich registrieren kann. Insbesondere ist es wie folgt.
Bei der Registrierung dieser URL sind einige Dinge zu beachten. Es hat eine URL
--https nur --localhost nicht verfügbar
Das ist der Punkt. Bei dieser Geschwindigkeit scheint die lokale Entwicklung schwierig zu sein. Mit ngrok können Sie die lokale URL jedoch vorübergehend nach außen veröffentlichen, sodass Sie sie bequem lokal entwickeln können, indem Sie die damit erstellte URL registrieren. Du kannst es schaffen. Es ist sehr praktisch.
Nachdem Sie den POST-Anforderungspfad für die Webhook-URL erstellt und in der Konsole festgelegt haben, überprüfen Sie die Anforderung über die Schaltfläche "Überprüfen". Stellen Sie sicher, dass Sie 200 Antworten erhalten. Weitere Informationen [hier](https://developers.line.biz/ja/docs/messaging-api/building-bot/#%E3%82%B3%E3%83%B3%E3%82%BD%E3% 83% BC% E3% 83% AB% E3% 81% A7% E3% 83% 9C% E3% 83% 83% E3% 83% 88% E3% 82% 92% E8% A8% AD% E5% AE% 9A% E3% 81% 99% E3% 82% 8B) Bitte.
Nachdem die Vorbereitungen für die Entwicklung abgeschlossen sind, möchte ich sie weiterentwickeln.
Zunächst möchte ich eine LINE-Anmeldefunktion erstellen, um die zum Senden und Empfangen von Nachrichten erforderlichen LINE-Informationen des Benutzers in die Datenbank zu stellen. Diese LINE-Information ist die "Benutzer-ID". Bitte beachten Sie, dass es sich nicht um die bei der ID-Suche verwendete LINE-ID handelt.
Der Anmeldefluss ist [hier](https://developers.line.biz/ja/docs/line-login/integrate-line-login/#%E3%83%AD%E3%82%B0%E3%82% A4% E3% 83% B3% E3% 81% AE% E3% 83% 95% E3% 83% AD% E3% 83% BC), aber wenn ich es noch einmal schreibe
redirect_uri
zum System um. Zu diesem Zeitpunkt wird auch eine Abfragezeichenfolge mit dem Autorisierungscode und dem Status an das System gesendet.Schauen wir uns den Code an, mit dem die Autorisierungs-URL für Schritt 1 erstellt wird.
app/controllers/auth_controller.rb
class AuthController < ApplicationController
def index
admin = Admin.find(params[:admin_id])
state = SecureRandom.hex(32)
session[:state] = state
redirect_to Line::Api::Oauth.new(admin).auth_uri(state)
end
end
/ admin /: admin_id / auth leitet basierend auf den LINE-Anmeldekontoinformationen des Zieladministrators zur Autorisierungs-URL weiter.
Da für CSRF-Maßnahmen ein Status erforderlich ist, wird auf der Anwendungsseite eine Zufallszahl generiert. Der Wert wird in der Sitzung gespeichert (wird bei der Verarbeitung nach der Autorisierung verwendet) und an Line :: Api :: Oauth # auth_uri
übergeben. Werfen wir einen Blick auf den darin enthaltenen Code.
app/models/line/api/oauth.rb
AUTH_URI = 'https://access.line.me/oauth2/v2.1/authorize'
def auth_uri(state)
params = {
response_type: 'code',
client_id: @admin.line_login_id,
redirect_uri: callback_uri,
state: state,
scope: 'openid',
prompt: 'consent', #Option, um sicherzustellen, dass die LINE-Authentifizierung zulässig ist
bot_prompt: 'aggressive' #Nach dem Anmelden wird ein Bildschirm angezeigt, in dem Sie gefragt werden, ob Sie sich mit dem offiziellen Konto anfreunden möchten, mit dem Sie verknüpft sind.
}
# NOTE: https://developers.line.biz/ja/docs/line-login/integrate-line-login/#making-an-authorization-request
"#{AUTH_URI}?#{params.to_query}"
end
Die detaillierte Bedeutung der Parameter finden Sie unter hier. Persönlich ist der Parameter "bot_prompt" praktisch, und nach dem Anmelden bei LINE wird auch der Bildschirm zum Hinzufügen von Freunden des entsprechenden offiziellen Kontos angezeigt. Daher hielt ich es für zweckmäßig, Nachrichten voneinander und voneinander zu bringen.
Wenn Sie auf die URL klicken, werden Sie zum Anmeldebildschirm weitergeleitet (siehe Abbildung unten).
Wenn die Anmeldung abgeschlossen und die Autorisierung abgeschlossen ist, werden Sie zu der zuvor festgelegten LINE-Anmelde-Rückruf-URL weitergeleitet. Nun, da wir zu / admin /: admin_id / callback
gehen, schauen wir uns den entsprechenden Code an.
app/controllers/callback_controller.rb
class CallbackController < ApplicationController
def index
admin = Admin.find(params[:admin_id])
#Wirf eine Ausnahme aus, wenn die Zustände unterschiedlich sind
raise Line::InvalidState unless params[:state] == session[:state]
line_user_id = Line::Api::Oauth.new(admin).line_user_id(params[:code])
User.create!(line_user_id: line_user_id)
render plain: 'LINE-Zusammenarbeit abgeschlossen!', status: :ok
end
end
CSRF-Maßnahmen werden ergriffen, indem der Wert des Status nach der Autorisierung mit dem Wert des Status der zuvor eingegebenen Sitzung verglichen wird. Danach erhalten Sie die LINE-Benutzer-ID. Speichern Sie es nach dem Erhalt in der Datenbank. Werfen wir einen Blick auf den Code zur Erfassung der Benutzer-ID.
app/models/line/api/oauth.rb
def line_user_id(code)
verify_id_token(access_token_data(code))['sub']
end
def access_token_data(code)
req_body = {
grant_type: 'authorization_code',
code: code,
redirect_uri: callback_uri, # NOTE:Es wird mit der in der Konsole des LINE-Anmeldekanals festgelegten "Rückruf-URL" verglichen.
client_id: @admin.line_login_id,
client_secret: @admin.line_login_secret
}
# NOTE: https://developers.line.biz/ja/docs/line-login/integrate-line-login/#get-access-token
res = conn.post do |req|
req.url '/oauth2/v2.1/token'
req.headers['Content-Type'] = 'application/x-www-form-urlencoded'
req.body = req_body
end
JSON.parse(handle_error(res).body)
end
def verify_id_token(access_token_data)
req_body = {
id_token: access_token_data['id_token'],
client_id: @admin.line_login_id
}
# NOTE: https://developers.line.biz/ja/reference/social-api/#verify-id-token
res = conn.post do |req|
req.url '/oauth2/v2.1/verify'
req.body = req_body
end
JSON.parse(handle_error(res).body)
end
Klicken Sie auf Access Token Acquisition API mit access_token_data
, um die Informationen zurückzugeben, und dann Wenn Sie die Social API ID Token Verification API aufrufen und erfolgreich sind, erhalten Sie Ihre Benutzer-ID.
Beachten Sie, dass die API für die Erfassung von Zugriffstoken "redirect_uri" übergibt, was genau mit dem im Autorisierungs-URI festgelegten "redirect_uri" übereinstimmen sollte. Sie können nicht viel tun, aber aus verschiedenen Gründen, wenn Sie beim Erstellen einer Autorisierungs-URL etwas als Abfrageparameter an redirect_uri
übergeben und mit einem Rückruf abrufen möchten, enthält die API für die Erfassung von Zugriffstoken diesen Abfrageparameter Wenn Sie es nicht an "redirect_uri" übergeben, wird ein Fehler angezeigt.
Nachdem der Benutzer nun eine Verknüpfung mit dem offiziellen LINE-Konto des Administrators herstellen konnte, möchte ich als nächstes die vom Benutzer im System gesendete LINE-Nachricht erhalten. Da die URL des Pfads "/ admin /: admin_id / webhook" in der Webhook-URL der Messaging-API angegeben ist, wird die Anforderung jedes Mal gesendet, wenn ein Ereignis (Freund hinzufügen, Nachricht blockieren usw.) im offiziellen Konto auftritt. Werden. Wenn also das Ereignis, das die ** Nachricht von dieser Anfrage gesendet hat, und die Person, die sie gesendet hat, die in der Datenbank gespeicherte LINE-Benutzer-ID ** ist, werden die LINE-Nachrichten vom Benutzer gesammelt, wenn Sie die Nachricht in der DB speichern. Sie können. Der Code für den Webhook-Controller ist unten.
app/controllers/webhook_controller.rb
class WebhookController < ApplicationController
protect_from_forgery with: :null_session
def create
admin = Admin.find(params[:admin_id])
bot = Line::Api::Bot.new(admin)
body = request.body.read
raise Line::InvalidSignatureError unless bot.validate_signature?(body, request.env['HTTP_X_LINE_SIGNATURE'])
events = bot.parse_events_from(body)
events.each do |event|
case event
when Line::Bot::Event::Message
Line::SaveReceivedMessage.new(admin).call(event)
end
end
render plain: 'success!', status: :ok
end
end
Da die Anforderung von außen kommt, machen Sie das CSRF-Token ungültig. Darüber hinaus müssen Sie Signaturvalidierung durchführen, um festzustellen, ob die Anforderung von der LINE-Plattform stammt. Es ist ein wenig kompliziert, aber es wird mit einem Edelstein namens line-bot-sdk-ruby gemacht, also lasst es uns verwenden.
Stellen Sie nach der Überprüfung fest, wie das Ereignis aussieht. Ich werde es verwenden, weil der Edelstein auch die Ereignisinformationen aus dem Anfragetext analysiert. Ich denke, es ist einfach, Ereignisse mit einer case-Anweisung zu verzweigen. Da "Line :: Bot :: Event :: Message" das Ereignis ist, bei dem die Nachricht eintrifft, wird zu diesem Zeitpunkt der Vorgang zum Speichern der Nachricht eingefügt. Der Code ist unten.
app/models/line/save_received_message.rb
module Line
class SaveReceivedMessage
def initialize(admin)
@admin = admin
end
def call(event)
user = User.find_by(line_user_id: event['source']['userId'])
resource = MessageText.new(content: event.message['text'])
Message.create!(sendable: user, receivable: @admin, resource: resource) if user.present?
end
end
end
Siehe hier für den Inhalt des Ereignisobjekts.
Überprüfen Sie abschließend die Funktion. Wenn Sie eine Nachricht senden
Sie können sehen, dass die Anforderung übersprungen und der Datensatz gespeichert wird. Das System kann nun die LINE-Nachricht des Benutzers empfangen und in die Datenbank stellen.
Als nächstes betrachten wir die LINE-Nachrichtenübertragung von System-> Benutzer, die das Gegenteil der vorherigen ist. Sie müssen Webhook nicht verwenden, drücken Sie einfach API zum Senden einer Push-Nachricht und fertig.
app/models/line/save_sent_message.rb
module Line
class SaveSentMessage
def initialize(admin)
@admin = admin
end
def call_with_text(user:, text:)
user = User.find_by(line_user_id: user.line_user_id)
if user.present?
Line::Api::Push.new(@admin).call_with_text(user: user, text: text)
resource = MessageText.new(content: text)
Message.create!(sendable: @admin, receivable: user, resource: resource)
end
end
end
end
app/models/line/api/push.rb
module Line::Api
class Push < Base
def call_with_text(user:, text:)
call(user: user, resource: Message::Text.new([text]))
end
private
def call(user:, resource:)
req_body = {to: user.line_user_id}.merge(resource.request_body)
# NOTE: https://developers.line.biz/ja/reference/messaging-api/#send-push-message
res = conn.post do |req|
req.url '/v2/bot/message/push'
req.headers['Content-Type'] = 'application/json'
req.headers['Authorization'] = "Bearer #{@admin.line_messaging_token}"
req.body = req_body.to_json
end
handle_error(res)
end
end
end
Es ist eine Funktionsprüfung. Tragen Sie es seitlich und schlagen Sie den Akkord von der Konsole aus.
Ein Datensatz wurde hinzugefügt.
Eine Nachricht wurde an LINE gesendet!
Mit dem oben Gesagten ist es möglich, zwischen dem Benutzer und dem System miteinander zu kommunizieren und den Inhalt zu verlassen. Ich denke, dass es in einem realen System komplizierter sein wird, aber ich hoffe, dies wird Ihnen helfen, etwas umzusetzen: beten Sie:
Recommended Posts