معظم وظيفتي اليومية هي TypeScript وPHP، ولكن هناك جزء كبير من الأدوات التي أتخلف عنها تولز.ديف والخدمات الصغيرة التي أكتب عنها هي Go، وفي كل مرة أقوم فيها بتوصيل عميل API جديد أصطدم بنفس الجدار. لديك استجابة JSON أمامك، وتحتاج إلى بنية Go التي json.Unmarshal سوف فك تشفيرها في. إن كتابة هذه البنية يدويًا أمر ممل بطريقة محددة للغاية: فهي ليست صعبة، إنها مجرد عبث، والأجزاء العبثية هي بالضبط المكان الذي ترتكب فيه الأخطاء. لذلك قمت ببناء محول في الموقع، وهذا هو الدليل له.
ليرة تركية؛DR: تولز محول هيكل JSON to Go يوزع مستند JSON ويصدر إعلانات نوع Go التي تصفه. تصبح الكائنات بنيات مضمنة، ويتم دمج صفائف الكائنات في بنية واحدة، ويحصل كل حقل على
json:"key"علامة ذلكencoding/jsonيعين البيانات مرة أخرى بشكل صحيح. تتبع أسماء الحقول اصطلاحات Go، لذاidيصبحIDوuser_urlيصبحUserURL. تبديل الأعداد الصحيحة إلىint64، أضفomitempty، وإعادة تسمية نوع الجذر. يعمل بالكامل من جانب العميل: لا يوجد تحميل، ولا تسجيل، ويعمل دون اتصال بالإنترنت.
ما هو محول بنية JSON to Go؟
يقوم محول بنية JSON to Go بتحويل مستند JSON إلى إعلانات نوع Go التي تصفه، حتى تتمكن من فك تشفير نفس البيانات باستخدام المكتبة القياسية '؛s encoding/json الحزمة بدلا من كتابة البنية باليد. يصبح كل كائن JSON بنية Go، وكل حقل يحمل json:"key" العلامة التي تعيد تعيينها إلى الاسم الأصلي، ويتم استنتاج الأنواع العددية من القيم. تصبح سلسلة JSON string، يصبح العدد الصحيح int، يصبح الرقم ذو العلامة العشرية float64، true و false يصبح bool، و null يصبح interface{}.
السبب وراء فائدة ذلك هو أن كائن JSON وبنية Go يصفان نفس الشكل، ومجموعة من الحقول المسماة بقيم مكتوبة، ولكن Go مكتوب بشكل ثابت وJSON ليس كذلك، لذلك يجب على البنية توضيح كل نوع مقدمًا. إن اشتقاق هذه الأنواع من استجابة العينة هو ميكانيكا خالصة، والميكانيكا التي تتم يدويًا عبر حمولة متداخلة هي المكان الذي تعيش فيه الأخطاء. يقوم المحول بالاشتقاق بشكل حتمي ويعيد لك كتلة الكتابة التي يتم تجميعها.
يجدر بنا أن نكون واضحين بشأن نصفي المشكلة، لأنهما ما يخطئ فيه المحول الساذج. الأول هو التسمية: اذهب فقط لتشفير الحقول المصدرة، تلك التي تحتوي على حرف أول كبير، وقواعد الوبر المجتمعي تريد الأحرف الأولى الشائعة بأحرف كبيرة بالكامل. والثاني هو العلامة: json:"..." يجب أن تحمل العلامة المفتاح الأصلي الدقيق أو json.Unmarshal يتخطى الحقل بصمت في وقت التشغيل دون أي خطأ. قم بأي خطأ وسيقوم فك التشفير بإرجاع بنية مليئة بالقيم الصفرية بينما يبدو كل شيء على ما يرام. الأداة تتعامل مع كليهما لك.
لماذا لا تكتب الهيكل باليد؟
هذا هو السؤال الصادق، لأنه بالنسبة لكائن مسطح ثلاثي الحقول، تكون الكتابة اليدوية للبنية أسرع من فتح الأداة. يكتسب المحول مكانه على الاستجابات غير المسطحة: حمولة تحتوي على كائنات متداخلة، ومصفوفات من الكائنات، وعشرين حقلاً حيث يوجد نصف المفاتيح snake_case والقليل منها عبارة عن أحرف أولية مثل id، url، و api_key.
في استجابة كهذه، تحتوي النسخة المكتوبة بخط اليد على ثلاثة أوضاع فشل قمت بالضغط عليها بشكل متكرر. تنسى تصدير حقل، لذلك يبقى بأحرف صغيرة و encoding/json يرفض ملئه. يمكنك الاستفادة من الحقل ولكنك تنسى العلامة، لذلك UserName يبحث عن مفتاح JSON يسمى UserName ولا يجد أبدا user_name. أو أنك أخطأت في التداخل، معلنة أن الحقل عبارة عن بنية عادية عندما يقوم JSON بتغليفه فعليًا في مصفوفة. لا يعد أي من هذه أخطاء في الترجمة. إنها مفاجآت وقت التشغيل التي تظهر كبيانات مفقودة، وتفقد وقتًا أطول في تصحيح أخطاء إحداها مما كنت ستقضيه في إنشاء البنية بأكملها.
يقوم المحول بإزالة الثلاثة. يقوم بتصدير كل حقل، ويكتب العلامة من المفتاح الحقيقي، ويقرأ شكل JSON الفعلي للاختيار بين البنية وشريحة من الهياكل. ما تلصقه هو ما تحصل على الأنواع من أجله.
وهنا القرار في جدول واحد.
| حالة | يستخدم | لماذا |
|---|---|---|
| كائن مسطح به حقلين أو ثلاثة حقول | اكتبها باليد | أسرع من فتح أي شيء |
| استجابة API متداخلة مع العديد من الحقول | محول هيكل JSON to Go | التسمية والعلامات هي المكان الذي تنكسر فيه الهياكل المكتوبة بخط اليد |
| أنت بحاجة إلى نفس شكل TypeScript | JSON إلى محول TypeScript | نفس الاستدلال، لغة مستهدفة مختلفة |
| تريد مخطط التحقق من الصحة، وليس الأنواع | مولد مخطط JSON | قواعد Draft-07 بدلاً من أنواع Go |
لماذا تختلف أسماء حقول Go عن مفاتيح JSON الخاصة بي؟
يؤدي هذا إلى تعثر الناس في المرة الأولى، لذا فهو يستحق الشرح بدلاً من الاختباء. اذهب '؛س encoding/json حزمة فقط الحراس وغير المارشالات تصديرها حقول البنية، والتي تعني الحقول التي يبدأ اسمها بحرف كبير. مفتاح JSON مثل user_name لا يمكن التعيين إلى غير مستورد user_name الحقل، لذلك يجب إعادة تسمية الحقل إلى شيء تم تصديره. تقوم الأداة بكتابة كل كلمة بالأحرف الكبيرة، ثم الدوران user_name في UserName.
علاوة على ذلك، فإن أدوات الوبر الخاصة بمجتمع Go '؛، هي القواعد التي بدأت بـ golint ويعيش في أدوات مثل staticcheck، يريد كتابة الأحرف الأولى الشائعة بأحرف كبيرة. لذا id يصبح IDلا Id؛ user_url يصبح UserURLلا UserUrl؛ و html_body يصبح HTMLBody. يعرف المحول المجموعة القياسية من الأحرف الأولى، ID، URL، API، HTTP، JSON، UUIDوالباقي، ويطبقها، بحيث يمر الإخراج بالروابط التي من المحتمل أن يقوم CI بتشغيلها.
القطعة التي تجعل إعادة التسمية آمنة هي العلامة. كل حقل يحصل على json:"user_name" العلامة التي تحمل المفتاح الأصلي بالضبط، لذلك في وقت التشغيل json.Unmarshal يقرأ مفتاح JSON user_name ويكتبها في UserName الحقل بغض النظر عن إعادة التسمية. توثق مقالة Go blog'؛s حول JSON وGo آلية العلامات هذه، وهذا هو السبب في استمرار فك تشفير الحقل المعاد تسميته بشكل صحيح. بدون العلامة، ستفشل البنية المعاد تسميتها في الملء بهدوء.
كيف يتم التعامل مع أرقام ومصفوفات الكائنات؟
يستحق جزءان من الاستدلال نظرة فاحصة لأنهما يختلفان في الجودة بين المحولات.
الأرقام أولا. لدى JSON نوع رقم واحد، لكن Go لا يحتوي على ذلك، لذا يجب على الأداة الاختيار. تصبح القيمة التي لا تحتوي على جزء كسري int، أو int64 إذا قمت بتشغيل هذا الخيار، وتصبح القيمة ذات العلامة العشرية float64. الحالة المثيرة للاهتمام هي مصفوفة تمزج بينها، مثل [9.5, 8, 7.2]. إذا كتبت الأداة ذلك كـ []int سوف تفشل في فك تشفير 9.5، لذلك فهو يوسع الشريحة بأكملها إلى []float64. أي مصفوفة يفرض فيها عنصر واحد نوعًا أوسع تحصل على النوع الأوسع لجميع العناصر، وهو الخيار الوحيد الذي يفك تشفير كل قيمة.
مصفوفات الكائنات هي المكان الآخر الذي تصبح فيه الحمولات الحقيقية مثيرة للاهتمام. لا تمنحك واجهة برمجة التطبيقات أبدًا مصفوفة حيث يحتوي كل كائن على مجموعة متطابقة من المفاتيح؛ يحتوي أحد العناصر على حقل يحذفه الآخرون، أو يوجد حقل فارغ هنا وغائب هناك. إذا قامت الأداة بإنشاء بنية من العنصر الأول فقط، فسوف تسقط المفاتيح التي تظهر لاحقًا. وبدلاً من ذلك، تقوم بدمج كل كائن في المصفوفة في بنية واحدة تتضمن كل مفتاح يحتوي عليه أي عنصر. وإذا أعطى عنصران نفس أنواع المفاتيح غير المتوافقة، على سبيل المثال رقمًا في واحد وسلسلة في عنصر آخر، فسيعود هذا الحقل إلى interface{} بدلاً من تخمين الأداة بشكل خاطئ أو فشلها تمامًا. والنتيجة هي نوع بنية واحد يمكنه فك تشفير المصفوفة بأكملها.
كيف أستخدم المحول؟
التدفق هو أربع خطوات. لصق كائن أو مصفوفة JSON في مربع الإدخال؛ إذا كنت تريد رؤية شكل الإخراج أولاً، قم بتحميل العينة. إعطاء نوع الجذر اسمًا، شيء من هذا القبيل User أو ApiResponseوتقوم الأداة بتنظيفه وتحويله إلى معرف Go صالح تم تصديره بحيث يتم تجميعه كما هو مكتوب. يختار int أو int64 للأعداد الصحيحة، وتشغيلها omitempty إذا كنت تريد استبعاد الحقول ذات القيمة الصفرية عند تشفير البنية لاحقًا مرة أخرى إلى JSON. ثم انقر فوق تحويل ونسخ البنية إلى ملفك .go ملف.
إذا كان JSON غير صالح، تقوم الأداة بالإبلاغ عن رسالة الخطأ الخاصة بالمحلل اللغوي '؛ بدلاً من الفشل بصمت، لذلك يتم العثور بسرعة على فاصلة زائدة طائشة أو مفتاح غير مقتبس. ولأن كل شيء يعمل في متصفحك، يمكنك لصق استجابة API حقيقية، بما في ذلك استجابة تحتوي على حقول خاصة، دون أن تترك جهازك. هذا النموذج من جانب العميل هو نفسه الموجود خلف بقية الموقع، الموضح في أدوات خصوصية البيانات عبر الإنترنت مرشد.
كيف يتناسب هذا مع أدوات JSON الأخرى؟
يعد محول البنية JSON to Go أحد أفراد عائلة محولات JSON الموجودة على الموقع، ويشتركون في نفس نواة التحليل. عندما تريد ترتيب JSON أولاً، فإن منسق JSON سيتم وضع مسافة بادئة والتحقق من صحتها، وهو أمر يستحق القيام به قبل التحويل حتى تتمكن من قراءة الشكل الذي أنت على وشك كتابته. عندما تكون لغتك المستهدفة هي TypeScript بدلاً من Go، فإن JSON إلى محول TypeScript يعمل على نفس الاستدلال وينبعث واجهات. عندما تحتاج إلى عقد التحقق من الصحة بدلاً من أنواع اللغات، فإن مولد مخطط JSON ينتج مخطط Draft-07، وعندما تكون الوجهة عبارة عن قاعدة بيانات PHP، فإن محول صفيف JSON إلى PHP يكتب مصفوفة حرفية.
الخيط الذي يربطهم جميعًا هو أنهم يتعاملون مع JSON كمصدر للبنية ويترجمون تلك البنية إلى أي شيء تتحدث به قاعدة التعليمات البرمجية الخاصة بك. إذا كنت تعمل عبر عدة لغات، فإن مجموعة أدوات مطور الويب يوضح التقرير كيف يتم تجميع هذه القطع معًا، و دليل أدوات الترميز يغطي مجموعة أوسع من المنسقين والمحولات.
مثال عملي من بناء خدمة Go
اسمحوا لي أن أجعل هذا ملموسا. منذ فترة كنت أكتب خدمة Go صغيرة تسحب البيانات من واجهة برمجة تطبيقات تابعة لجهة خارجية وتعيد الكشف عن نسخة مصغرة منها. كانت استجابة البائع & #39؛ كائنًا متداخلًا: سجل عالي المستوى مع owner كائن فرعي، أ tags مجموعة من السلاسل، و scores المصفوفة التي، بشكل مزعج، تم خلط الأعداد الصحيحة والكسور العشرية اعتمادًا على الحقل. الكتابة اليدوية للبنية تعني الحصول على owner التعشيش الصحيح، ووضع علامات على كل snake_case المفتاح، وتحديد ما يجب فعله بشأن تلك المصفوفة المختلطة.
لقد قمت بلصق استجابة العينة في المحول، وقمت بتسمية نوع الجذر على اسم المورد، واستعدت بنية باستخدام Owner باعتبارها بنية متداخلة مضمنة، Tags مثل []string، و Scores اتسعت بشكل صحيح إلى []float64. ال id خرج الميدان كما ID مع أ json:"id" العلامة، لذلك تم تمريرها وفك تشفير المفتاح الحقيقي. لقد قمت بنسخها مباشرة إلى حزمة العميل وانتقلت إلى المنطق، وهو المكان الذي أردت بالفعل قضاء وقتي فيه. لم تكن البنية هي الجزء المثير للاهتمام من العمل، وكان توليدها يعني أنها توقفت عن كونها جزءًا من العمل.
السبب الذي يجعلني أصل إلى المحول بدلاً من البنية المكتوبة بخط اليد في هذه المواقع ليس الكسل، بل هو أن الأجزاء الميكانيكية، والتصدير، ووضع العلامات، والتداخل، هي بالضبط الأجزاء التي أخطأت فيها عندما أفكر في المنطق بدلاً من ذلك. تفريغها إلى أداة حتمية يعني أن البنية صحيحة في الترجمة الأولى، وفك التشفير الصحيح في التشغيل الأول، والذي يوفر جلسة تصحيح أخطاء حقيقية على الحمولة المتداخلة. عندما أحتاج إلى إعادة تشفير البنية للبقاء على قيد الحياة أيضًا، أقوم بتشغيلها omitempty لذا تظل القيم الصفرية خارج الإخراج، وتظهر العلامات على أنها json:"key,omitempty" جاهز لتلك الرحلة ذهابًا وإيابًا.
ما هي الحدود التي تستحق المعرفة عنها؟
بعض الحواف الصادقة. الأول هو null. جسون null لا يحمل أي معلومات عن النوع من تلقاء نفسه، لذا فإن هذا الحقل هو null في العينة الخاصة بك يتم كتابتها كـ interface{}. لا يوجد شيء يمكن للأداة استنتاجه هناك؛ إذا كنت تعرف النوع الحقيقي، قم بتغييره في المحرر الخاص بك بعد اللصق، أو قم بتغذية المحول بعينة حيث يكون لهذا الحقل قيمة حقيقية بحيث يمكن اشتقاق النوع. هذه خاصية للبيانات وليست عيبًا في الأداة.
والثاني هو الدقة الرقمية، وهي خاصية لتحليل JSON بشكل عام وليس هذا المحول على وجه التحديد. تقوم الأداة بتحليل JSON الخاص بك باستخدام محلل JSON للمتصفح '؛s، والذي يمثل الأرقام على شكل عوامات مزدوجة الدقة، لذا فإن الأعداد الصحيحة التي تتجاوز تقريبًا 2 إلى الطاقة 53 تفقد الدقة في وقت التحليل، قبل أن تراها الأداة. التي تم إنشاؤها int64 المجال واسع بما فيه الكفاية ل يمسك معرف كبير، ولكن إذا وصل المعرف كرقم JSON مكشوف بهذا الحجم، فقد قام التحليل بتقريبه بالفعل. بالنسبة للمعرفات الصحيحة الكبيرة حقًا، فإن الحركة القوية هي حملها كسلاسل في JSON، مما يبقيها دقيقة ويتيح لك كتابة الحقل كـ string.
والثالث هو أن الاستدلال هو نقطة البداية، وليس الإنجيل. تمنحك الأداة الأنواع التي تدعمها العينة، ولكنك وحدك من يعلم أن الحقل الذي يصادف أنه عدد صحيح في هذه الاستجابة هو في الواقع عدد لاغي، أو أن أ float64 ينبغي أن يكون json.Number لتجنب فقدان الدقة. تعامل مع الإخراج باعتباره مسودة أولى صحيحة يمكنك تحسينها، وليس عقدًا منحوتًا في الحجر. وهذا ينطبق على كل مولد JSON إلى نوع، بأي لغة.
أخيرًا، ينتج المحول بنيات متداخلة مضمنة، والتي تحافظ على الشكل بأكمله في إعلان واحد يمكنك لصقه ككتلة. هذا هو النمط الأكثر شيوعًا والأكثر قابلية للقراءة للبنية التي تم إنشاؤها، وهو ما شاعته الأدوات الموجودة في نظام Go البيئي. إذا كنت تفضل الحصول على أنواع مسماة منفصلة للكائنات الفرعية المعاد استخدامها بعمق، فهذا هو إعادة البناء التي تقوم بها يدويًا بمجرد وجود الإصدار المضمن في المحرر الخاص بك، وعادةً ما يكون مستخرجًا مدته خمس ثوانٍ باستخدام IDE الخاص بك.
الأسئلة المتداولة
ما هو محول بنية JSON to Go؟ يقوم محول بنية JSON to Go بتحويل مستند JSON إلى إعلانات نوع Go التي تصفه. يصبح كل كائن بنية، ويحصل كل حقل على json:"؛key"؛ العلامة، ويتم استنتاج أنواع القيم، حتى تتمكن من إلغاء تنظيم نفس البيانات باستخدام التشفير/json دون كتابة البنية يدويًا.
كيف يمكنني تحويل JSON إلى بنية Go؟ الصق JSON الخاص بك في مربع الإدخال، وأدخل اسمًا لنوع الجذر، واختر خيارات الأعداد الصحيحة والعلامات، ثم انقر فوق تحويل. تقوم الأداة بطباعة تعريفات بنية Go باستخدام علامات json التي يمكنك نسخها مباشرة إلى ملف.go.
لماذا تختلف أسماء حقول Go عن مفاتيح JSON الخاصة بي؟ يقوم Go فقط بتشفير الحقول المصدرة، لذلك تتم كتابة اسم كل حقل بأحرف كبيرة، ويتم إنشاء الأحرف الأولى الشائعة بأحرف كبيرة لمطابقة golint. Json:"؛..."؛ تحتفظ العلامة الموجودة في كل حقل بالمفتاح الأصلي، لذلك لا يزال json.Unmarshal يقوم بتعيين البيانات بشكل صحيح على الرغم من الحقل المعاد تسميته.
كيف يتم تعيين أرقام JSON لأنواع Go؟ يصبح الرقم الصحيح int، أو int64 إذا قمت بتمكين هذا الخيار، ويصبح الرقم ذو العلامة العشرية float64. عندما يمزج المصفوفة بين الأعداد الصحيحة والكسور العشرية لنفس الموضع، يتم توسيع النوع إلى float64 بحيث تناسب كل قيمة.
كيف يتم التعامل مع صفائف الكائنات؟ يتم دمج مصفوفة من الكائنات في بنية واحدة تتضمن كل مفتاح يحتوي عليه أي عنصر. إذا أعطى عنصران نفس أنواع المفاتيح غير المتوافقة، يصبح هذا الحقل واجهة {} وبالتالي تظل البنية تغطي المصفوفة بأكملها.
ماذا يحدث للقيم الخالية؟ لا يعطي JSON null أي معلومات عن النوع من تلقاء نفسه، لذلك تتم كتابة الحقل كواجهة {}. إذا كنت تعرف النوع الحقيقي، فقم بتغييره في المحرر الخاص بك بعد اللصق، أو قم بتوفير قيمة مثال غير فارغة في JSON حتى يمكن استنتاج النوع.
هل تم تحميل json الخاص بي في أي مكان؟ لا. يحدث التحويل بالكامل في متصفحك باستخدام JavaScript على جهازك. لا يتم تحميل JSON الخاص بك أو تسجيله أو تخزينه مطلقًا، وتستمر الأداة في العمل مع الشبكة المنفصلة بمجرد تحميل الصفحة.
هل محول البنية JSON to Go مجاني؟ نعم. إنه مجاني تمامًا بدون تسجيل ولا علامة مائية ولا حد أقصى للاستخدام. قم بتحويل العديد من مستندات JSON إلى هياكل Go حسب حاجتك للمشاريع الشخصية أو التجارية.



