دخول
لأتمتة المنزل ، كنت أستخدم HomeAssistant لفترة طويلة. بمجرد أن يسألني أحد الأصدقاء ، لماذا يقولون إن HomeAssistant لديها القدرة على الإشارة فقط إلى الموقع الحالي للمتتبع على الخريطة ، لكن لا يمكن عرض المسار بالكامل؟ منذ ذلك الحين ، استولت علي هذه الفكرة. وبمجرد أن أدركت أنني أريد حقًا الحصول على هذه الوظيفة الآن. كل من يهتم بما جاء من هذا ، مرحبا بكم في القط ...
استكشاف
في الواقع ، لعرض المسار الذي تحتاجه للحصول على مجموعة من النقاط مع الإحداثيات ، لذلك كانت الخطوة الأولى هي معرفة أين تقوم HomeAssistant بتخزين البيانات اللازمة (إن وجدت) وكيفية إخراجها من هناك. أدت دراسة قصيرة للمصدر الأساسي على الفور إلى الحل: تحتاج إلى وحدة تسجيل مدرجة لتسجيل حالة المستشعرات المطلوبة في قاعدة البيانات في نقاط مختلفة في الوقت المناسب ، وكذلك وحدة المحفوظات ، والتي تتيح لك الحصول على البيانات من قاعدة البيانات بطريقة جميلة. تحتوي الوحدة النمطية للتاريخ على
واجهة برمجة تطبيقات REST موثقة جيدًا. ما تحتاجه!
بعد ذلك ، تحتاج إلى عرض البيانات المستلمة بطريقة ما على الخريطة. هناك العديد من الخدمات المختلفة التي تتيح لك عرض تاريخ الحركات. ربما حاولت بعيدًا عنهم جميعًا ، لكنني سأسمح لنفسي ببضع كلمات عن الكلمات التي راجعت:
A. ياندكس وجوجل. في الواقع لتلبية احتياجاتي ، هناك كل شيء وأكثر ، ولكن بسبب الخدمات المدفوعة والقيود القوية على الإصدارات المجانية ، فإنها لم تناسبني على الفور. على سبيل المثال ، تسمح Yandex بالاستخدام المجاني فقط للمشاريع المفتوحة (أي ، يجب أن يكون أي شخص قادرًا على فتح المورد الخاص بك في أي وقت والاستفادة من قدراته) ، ناهيك عن القيود الأخرى على عدد الطلبات. كسول فقط لم يكتب عن التغييرات في سياسات جوجل فيما يتعلق api. في الوقت الحالي ، كما أفهمها ، يتم دفع كل طلب لتعيين api أو direction api ، وكلما زادت الطلبات - أرخص. ومع ذلك ، يتم منح حد مجاني قدره 200 دولار لكل مستخدم لديه بطاقة مصرفية متصلة بحسابه. يتم دفع كل شيء على الفور من بطاقتك. ربط البطاقة بحساب ليس هو طريقنا.
صحيح إذا ارتكبت خطأ في مكان ما حول جوجل و / أو ياندكس.
B. مجموعة من خرائط OpenRouteService و OpenRouteService. من حيث المبدأ ، لا تختلف القدرات كثيرًا عن google أو yandex (على أي حال ، لم ألاحظ). مجاني تمامًا (هناك قيود على عدد الطلبات في اليوم والدقيقة ، إذا تم تجاوزها ، يُنصح بالاتصال بالدعم ... لا يوجد أي وصف للتعريفات المدفوعة على الإطلاق). ومع ذلك ، تبين أن استخدام مورد خرائط OpenRouteService غير مريح (التحميل الطويل للتطبيق والقائمة الواسعة المزعجة على اليسار ، والتي يتم فتحها افتراضيًا ولا يتم تعطيلها بواسطة API ، علاوة على ذلك ، الخدمة لا تفتح بشكل صحيح من الأجهزة المحمولة). في الإنصاف ، يمكن وضع خرائط OpenRouteService على الخادم الخاص بك ومن الممكن تمامًا أنه يمكنك تكوين كل شيء بنفسك.
في. Mapbbcode . لقد عثرت على تطبيق مثير للاهتمام للبطاقات بتنسيق بسيط. من حيث المبدأ ، فإن المشروع مناسب تمامًا لمهمتي ، ومع ذلك ، من هذه المقالة تعلمت عن
Leaflet وقررت الانتقال إلى المصدر. في النهاية ، توقف في ذلك ...
R. النشرة. مكتبة js مفتوحة المصدر جيدة جدًا للخرائط ، سهلة التعلم وموثقة جيدًا. من الرقائق: يتيح لك استخدام البلاط من العديد من الخدمات (خرائط openstreet ، و yandex ، و google ، و mapbox ، و Microsoft ، وما إلى ذلك). بالإضافة إلى ذلك ، استخدمت البرنامج المساعد لـ
leaflet.polylineDecorator للإشارة إلى اتجاه الحركة على الخريطة.
تجدر الإشارة إلى أن الموردين الأخيرين قيد النظر لا يدعمان "المسارات" ، أي أنهم لا يعرفون كيفية توصيل النقاط على طول الطرق و / أو الأرصفة الموجودة ، ولكنهم ببساطة يربطون النقاط بخط مستقيم. بالنسبة لي شخصيا ، هذه ليست مشكلة ، ولكنها خطوة واعية. إذا كنت بحاجة إلى التنقل على الطرق ، فأنت بحاجة إلى البحث في اتجاه google أو yandex أو خدمة openrouteserv المدفوعة.
تطبيق
طلب الوحدة النمطية للتاريخ عبر REST-API بسيط للغاية (فيما يلي سيكون الرمز باللغة HomeAssistant ، أي python) ويسمح لك بالحصول على الإجابة في شكل JSON سهلة الفهم:
response = requests.get(self._haddr + '/api/history/period/' + dayBegin + '?filter_entity_id=' + self._myid, headers={'Authorization': 'Bearer ' + self._token, 'content-type': 'application/json'}) data = response.json()[0]
هنا self._haddr هو عنوان HA الخاص بك كما هو محدد في إعدادات الواجهة الأمامية ، self._my هو معرف الجهاز لـ device_tracker ، الذي سنبنيه ، dayBegin هو بداية الفترة لعرض المسار ، لقد اخترت بداية اليوم الحالي بشكل افتراضي ، self._token هو رمز طويل العمر للوصول إلى واجهة برمجة التطبيقات ، والتي يمكن الحصول عليها في واجهة HomeAssistant.
عندما يكون الكائن الذي نحاول عرض تاريخه على الخريطة ثابتًا لفترة طويلة أو يتحرك ببطء شديد ، فسنحصل على مجموعة من النقاط الموجودة عن كثب وتسد الخريطة. لتصحيح الموقف ، اترك صفيف الإحداثيات الناتج خلال الفلتر: إذا كانت المسافة بين النقطة السابقة والقادمة أقل من 100 متر ، فلا تعرض النقطة على الخريطة. لحساب المسافات بين نقطتين متجاورتين ، نستخدم صيغة مبسطة
بتقريب متساوي الشكل . ينطبق التقريب عندما لا تتجاوز المسافة بين النقاط المجاورة عدة كيلومترات:
def getDistance(self, latA, lonA, latB, lonB): dst = 0 latRadA = math.radians(latA) lonRadA = math.radians(lonA) latRadB = math.radians(latB) lonRadB = math.radians(lonB) x = latRadB - latRadA y = (lonRadB-lonRadA)*math.cos((latRadB+latRadA)*0.5) dst = 6371*math.sqrt(x*x+y*y) return dst
هنا التوقيت الصيفي هي المسافة بالكيلومترات.
وصف API Leaflet هنا لا يرى هذه النقطة. لهذا - على
الموقع الرسمي . تعمل الوحدة النمطية كما يلي: كل n ثانية (قمت بضبطها على 300) ، يتم تقديم طلب إلى سجل اليوم الخاص بالشيء الذي يهمني. يتم تشغيل مجموعة الإحداثيات الناتجة من خلال مرشح المسافة ، مما يقلل من عدد النقاط. بعد ذلك ، في المجلد الذي يحتوي على تكوين HomeAssistant في المجلد www ، يتم تشكيل ملفين: index.html و route.html. يحتوي ملف route.html على كل منطق إنشاء الخريطة. وملف index.html هو اختراق حياة لمنع التخزين المؤقت للصفحة. بشكل افتراضي ، تقوم ميزة HomeAssistant بتخزين كل ما هو ممكن مؤقتًا ، وساعدت إعادة تعيين ذاكرة التخزين المؤقت فقط على تحديث البيانات الموجودة على البطاقة ، وهو أمر غير مقبول بالطبع. في ملف index.html ، يتم استدعاء محتويات route.html ، ولكن باستخدام معلمة عشوائية تم إنشاؤها ديناميكيًا ، والتي تتيح لك دائمًا طلب الإصدار الحالي من route.html من الخادم:
src = 'route.html?datetime=' + (new Date()).getTime() + Math.floor(Math.random() * 1000000)
قليلا عن الأمن
تم تصميم HomeAssistant بحيث تكون جميع الملفات الموجودة داخل دليل www عامة ، أي يمكن فتح أي ملف داخل دليل www في أي مستعرض دون أي إذن ، ومعرفة الرابط المباشر. في حالة الوحدة الخاصة بي ، يكون هذا الرابط هو:
your_address_homeassistant / local / route / index.html . إذا لم يكن هذا أمرًا بالغ الأهمية بالنسبة لك ، فيمكنك تخطي هذا القسم. ذهبت أبعد من ذلك بقليل وفسدت إذن إلى الصفحة مع طرق. لهذا ، استخدمت nginx (يمكنك اختيار خادم ويب آخر مع دعم وكيل عكسي) كخادم وكيل. يحتوي موقع HomeAssistant على
إرشادات رسمية لإعداد هذا التكوين. بعد إعداد الخادم الوكيل والتحقق من العملية ، تحتاج إلى إضافة إذن إلى الصفحات الضرورية في تكوين nginx:
location /local/route/route.html { proxy_pass http://localhost:8123/local/route/route.html; proxy_set_header Host $host; proxy_redirect http:// https://; proxy_http_version 1.1; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection $connection_upgrade; auth_basic "Unauthorized"; auth_basic_user_file /etc/nginx/.htpasswd; }
ثم قم بإنشاء الملف "/etc/nginx/.htpasswd" وتنفيذ الأوامر التالية في وحدة التحكم:
sh -c "echo -n 'admin:' >> /etc/nginx/.htpasswd" sh -c "openssl passwd -apr1 >> /etc/nginx/.htpasswd"
المشرف - استبدال تسجيل الدخول المطلوب.
بعد ذلك ، أعد تشغيل nginx وتحقق: عند محاولة فتح صفحة بمسار ، يجب أن يطلب المستعرض اسم مستخدم وكلمة مرور. ألاحظ أن هذا تفويض منفصل لا علاقة له بتصريح HomeAssistant نفسه.
استنتاج
ربما كل ما يمكن أن يقال عن هذه الوحدة.
من المهتمين ،
هنا هو رابط إلى الوحدة النمطية. ضع الملف على طول المسار: config_folder_homeassistant / custom_components / route / sensor.py ، لا تنس الحقوق.
إذا لم يكن موجودًا ، فقم بإنشاء مجلد config_folder_homeassistant / www ومنحه الحقوق المناسبة.
في ملف التكوين config.yaml ، اكتب الأسطر التالية:
sensor: - platform: route name: route entityid: your_device_tracker_entity_id haddr: your_address_homeassistant token: your_long_life_token
هنا your_device_tracker_entity_id هو معرّف الجهاز device_tracker ، your_address_homeassistant هو العنوان الخارجي لـ HomeAssistant الخاص بك ، your_long_life_token هو رمز الوصول الذي تم استلامه مسبقًا في الواجهة الأمامية لـ HomeAssistant لاستخدام واجهة برمجة تطبيقات REST.
بعد ذلك ، أعد تشغيل HomeAssistant واستمتع. ستكون الخريطة متاحة من خلال رابط مباشر:
your_address_homeassistant / local / route / index.html . إذا كنت ترغب في ذلك ، يمكنك إضافته إلى قائمة HA باستخدام panel_iframe أو إلى أي نافذة HA عبر بطاقة لوفيلاس "iframe".
هذا كل شيء ، شكرا لاهتمامكم.
UPD:إضافة
رابط إلى جيثب. تم تعديل بعض الأماكن (تمت إزالته من التكوين haddr ، والحصول تلقائيًا على config_dir ، وإضافة القدرة على ضبط المنطقة الزمنية الخاصة بي)
وكيف يبدو كل شيء؟ الحذر ، Bluer!