تجزیه JSON در جاوا را با منیفولد انقلابی کنید
توسعه دهندگان جاوا اغلب به جاوا اسکریپت به دلیل سهولت تجزیه JSON حسادت می کنند. اگرچه جاوا استحکام بیشتری را ارائه می دهد، اما تمایل دارد کار و کد دیگ بخار بیشتری را شامل شود. به لطف پروژه Manifold، جاوا اکنون این پتانسیل را دارد که در تجزیه و پردازش فایل های JSON از جاوا اسکریپت پیشی بگیرد. منیفولد مجموعه ای انقلابی از پسوندهای زبان برای جاوا است که به طور کامل نحوه مدیریت JSON را تغییر می دهد (و خیلی بیشتر …).
شروع کار با منیفولد
کد این آموزش را می توانید در صفحه GitHub من پیدا کنید. منیفولد نسبتاً جوان است اما در حال حاضر توانایی هایش بسیار زیاد است. شما می توانید در وب سایت و کانال Slack در مورد این پروژه اطلاعات بیشتری کسب کنید. برای شروع، باید افزونه Manifold را نصب کنید، که در حال حاضر فقط برای IDE های JetBrains در دسترس است. این پروژه از نسخه های LTS جاوا، از جمله آخرین JDK 19 پشتیبانی می کند.
میتوانیم با رفتن به بازار و جستجوی Manifold، افزونه را از رابط کاربری تنظیمات IntelliJ/IDEAs نصب کنیم. این افزونه مطمئن می شود که IDE با کار انجام شده توسط افزونه Maven/Gradle برخورد نمی کند.
منیفولد از چندین پروژه کوچکتر تشکیل شده است که هر کدام یک پسوند زبان سفارشی را ارائه می دهند. امروز، یکی از این پسوندها را مورد بحث قرار خواهیم داد، اما چیزهای بیشتری برای بررسی وجود دارد.
راه اندازی یک پروژه Maven
برای نشان دادن منیفولد، از یک پروژه ساده Maven استفاده می کنیم (این پروژه با Gradle نیز کار می کند). ابتدا باید نسخه منیفولد فعلی را از وب سایت آنها Paste کنیم و وابستگی های لازم را اضافه کنیم. وابستگی اصلی برای JSON است manifold-json-rt
وابستگی وابستگی های دیگری را می توان برای پشتیبانی از YAML، XML و CSV اضافه کرد. ما باید این را به آن اضافه کنیم pom.xml
فایل در پروژه
من از طنزی که کاهش دیگ بخار برای JSON با مقدار زیادی از پیکربندی در اسکریپت ساخت Maven شروع می شود آگاه هستم. اما این پیکربندی است، نه «کد واقعی» و عمدتاً کپی و چسباندن است. توجه داشته باشید که اگر می خواهید این کد را کاهش دهید، کد معادل Gradle در مقایسه کوتاه است.
این خط باید وارد بخش خصوصیات شود:
<manifold.version>2023.1.5</manifold.version>
وابستگی هایی که ما استفاده می کنیم عبارتند از:
<dependencies>
<dependency>
<groupId>systems.manifold</groupId>
<artifactId>manifold-json-rt</artifactId>
<version>${manifold.version}</version>
</dependency>
پلاگین کامپایل دیگ بخاری است که منیفولد را در بایت کد می بافد و آن را برای ما یکپارچه می کند. این آخرین بخش از راه اندازی پوم است:
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.8.0</version>
<configuration>
<source>19</source>
<target>19</target>
<encoding>UTF-8</encoding>
<compilerArgs>
<!-- Configure manifold plugin-->
<arg>-Xplugin:Manifold</arg>
</compilerArgs>
<!-- Add the processor path for the plugin -->
<annotationProcessorPaths>
<path>
<groupId>systems.manifold</groupId>
<artifactId>manifold-json</artifactId>
<version>${manifold.version}</version>
</path>
</annotationProcessorPaths>
</configuration>
</plugin>
</plugins>
</build>
با تکمیل راهاندازی، بیایید وارد کد شویم.
تجزیه JSON با منیفولد
ما یک نمونه فایل JSON را در فهرست پروژه تحت سلسله مراتب منابع قرار می دهیم. من این فایل را در زیر قرار دادم src/main/resources/com/debugagent/json/Test.json
:
{
"firstName": "Shai",
"surname": "Almog",
"website": "https://debugagent.com/",
"active": true,
"details":[
{"key": "value"}
]
}
در کلاس اصلی، پروژه Maven را بهروزرسانی میکنیم و متوجه خواهید شد که یک کلاس تست جدید ظاهر میشود. این کلاس به صورت پویا توسط Manifold بر اساس فایل JSON ایجاد می شود. اگر JSON را تغییر دهید و Maven را رفرش کنید، همه چیز یکپارچه بهروزرسانی میشود. درک این نکته مهم است که منیفولد یک تولید کننده کد نیست. JSON را که به تازگی نوشتیم را در بایت کد کامپایل می کند.
کلاس Test دارای چندین قابلیت داخلی است، مانند API سازنده ایمن که به شما امکان می دهد اشیاء JSON را با استفاده از متدهای سازنده بسازید. همچنین میتوانید اشیاء تودرتو تولید کنید و JSON را با استفاده از عبارت به رشته تبدیل کنید write()
و toJson()
مواد و روش ها.
یعنی اکنون می توانیم بنویسیم:
Test test = Test.builder().withFirstName("Someone")
.withSurname("Surname")
.withActive(true)
.withDetails(List.of(
Test.details.detailsItem.builder().
withKey("Value 1").build()
))
.build();
که JSON زیر را چاپ می کند:
{
"firstName": "Someone",
"surname": "Surname",
"active": true,
"details": [
{
"key": "Value 1"
}
]
}
ما به طور مشابه می توانیم یک فایل JSON را با استفاده از کدهایی مانند زیر بخوانیم:
Test readObject = Test.load().fromJson("""
{
"firstName": "Someone",
"surname": "Surname",
"active": true,
"details": [
{
"key": "Value 1"
}
]
}
""");
به استفاده از جاوا 15 توجه کنید TextBlock
نحو برای نوشتن یک رشته طولانی را load()
متد یک شی را برمی گرداند که شامل API های مختلف برای خواندن JSON است. در این صورت از الف خوانده می شود String
اما API هایی برای خواندن آن از یک URL، فایل و غیره وجود دارد.
منیفولد از فرمتهای مختلفی از جمله CSV، XML و YAML پشتیبانی میکند و به شما امکان میدهد هر یک از این فرمتها را بدون نوشتن کد دیگ بخار یا به خطر انداختن ایمنی نوع تولید و تجزیه کنید. برای اضافه کردن این پشتیبانی، باید وابستگیهای اضافی را به فایل pom.xml اضافه کنیم:
<dependency>
<groupId>systems.manifold</groupId>
<artifactId>manifold-csv-rt</artifactId>
<version>${manifold.version}</version>
</dependency>
<dependency>
<groupId>systems.manifold</groupId>
<artifactId>manifold-xml-rt</artifactId>
<version>${manifold.version}</version>
</dependency>
<dependency>
<groupId>systems.manifold</groupId>
<artifactId>manifold-yaml-rt</artifactId>
<version>${manifold.version}</version>
</dependency>
</dependencies>
با این وابستگیهای اضافی، این کد همان دادههای فایل JSON را چاپ میکند… با test.write().toCsv()
خروجی خواهد بود:
"firstName","surname","active","details"
"Someone","Surname","true","[manifold.json.rt.api.DataBindings@71070b9c]"
توجه داشته باشید که خروجی مقادیر جدا شده با کاما (CSV) شامل اطلاعات سلسله مراتبی نیست. این یک محدودیت در قالب CSV است و تقصیر منیفولد نیست.
با test.write().toXml()
خروجی آشنا و به طرز شگفت آوری مختصر است:
<root_object firstName="Someone" surname="Surname" active="true">
<details key="Value 1"/>
</root_object>
با test.write().toYaml()
ما دوباره یک چاپ آشنا دریافت می کنیم:
firstName: Someone
surname: Surname
active: true
details:
- key: Value 1
کار با JSON Schema
منیفولد همچنین با طرح JSON به طور یکپارچه کار می کند و به شما امکان می دهد قوانین و محدودیت های سختگیرانه ای را اعمال کنید. این به ویژه هنگام کار با تاریخ ها و شماره ها مفید است. منیفولد بهطور یکپارچه کد بایتی را ایجاد/بهروزرسانی میکند که به طرحواره میپیوندد و کار با دادههای پیچیده JSON را بسیار آسانتر میکند.
این طرح از پروژه Manifold github کپی و جایگذاری شده است:
{
"$schema": "http://json-schema.org/draft-07/schema#",
"$id": "http://example.com/schemas/User.json",
"type": "object",
"definitions": {
"Gender": {
"type": "string",
"enum": ["male", "female"]
}
},
"properties": {
"name": {
"type": "string",
"description": "User's full name.",
"maxLength": 80
},
"email": {
"description": "User's email.",
"type": "string",
"format": "email"
},
"date_of_birth": {
"type": "string",
"description": "Date of uses birth in the one and only date standard: ISO 8601.",
"format": "date"
},
"gender": {
"$ref" : "#/definitions/Gender"
}
},
"required": ["name", "email"]
}
این طرحی نسبتاً ساده است، اما مایلم در اینجا توجه شما را به چند چیز معطوف کنم. نام و ایمیل را در صورت لزوم تعریف می کند. به همین دلیل است که وقتی سعی می کنیم یک a ایجاد کنیم User
شی با استفاده از سازنده در Manifold، the build()
روش به هر دو پارامتر نیاز دارد:
User.builder("Name", "email@domain.com")
این فقط شروع است… این طرح شامل یک تاریخ است. تاریخ ها چشم انداز دردناکی در JSON هستند، استانداردسازی ضعیف و مملو از مشکلات است. این طرح همچنین شامل یک فیلد جنسیتی است که در واقع یک عدد است. همه اینها با استفاده از کلاس های رایج جاوا مانند LocalDate به معنایی ایمن نوع تبدیل می شود:
User u = User.builder("Name", "email@domain.com")
.withDate_of_birth(LocalDate.of(1999, 10, 11))
.withGender(User.Gender.male)
.build();
این را می توان با واردات ثابت کوتاه تر کرد، اما اصل ایده واضح است. JSON به طور موثر بومی جاوا در Manifold است.
نوک کوه یخ
منیفولد یک پروژه قدرتمند و هیجان انگیز است. تجزیه JSON در جاوا را متحول می کند، اما این تنها یک بخش کوچک از کاری است که می تواند انجام دهد!
ما در این پست فقط سطح قابلیت های آن را ترسیم کرده ایم. در مقاله بعدی، عمیقتر به منیفولد میپردازیم و برخی ویژگیهای غیرمنتظره اضافی را بررسی میکنیم.
لطفا تجربیات و نظرات خود را در مورد منیفولد در قسمت نظرات به اشتراک بگذارید. اگر سوالی دارید، در پرسیدن دریغ نکنید.