361 قراءة٪ s
361 قراءة٪ s

في عام 2025، الموسيقى المحلية على iPhone هي كابوس - لذلك أنا بنيت طريقتي الخاصة

بواسطة Oleg Pustovit12m2025/05/22
Read on Terminal Reader

طويل جدا؛ ليقرأ

في عام 2025 ، ستكون لعب الموسيقى الخاصة بك على جهاز iPhone صعباً جديداً ، ما لم تتمكن من الدفع عن Apple أو التحكم في محيط من القيود.
featured image - في عام 2025، الموسيقى المحلية على iPhone هي كابوس - لذلك أنا بنيت طريقتي الخاصة
Oleg Pustovit HackerNoon profile picture
0-item

في عام 2025 ، ستكون لعب الموسيقى الخاصة بك على جهاز iPhone صعباً جديداً ، ما لم تتمكن من دفع أبل أو التحليق في محيط من القيود.

في عام 2025 ، ستكون لعب الموسيقى الخاصة بك على جهاز iPhone صعباً جديداً ، ما لم تتمكن من دفع أبل أو التحليق في محيط من القيود.

لماذا كنت قد وضعت منصة أندرويد الخاصة بي

مثل الكثير من الناس، لقد استخدمت الكثير من التقييمات، بعض من خلال Apple (iCloud، Apple Music)، والبعض الآخر فقدت في منصات عشوائية (مثل Netflix، والتي أسفرت عن دفعها حتى الآن).

في البداية كنت أعتقد أنني ستواصل استخدام مكتبة موسيقى iCloud لمكافحة الموسيقى بين الأجهزة ، ولكن بعد إلغاء ترخيص Apple Music ، أوقفت المساواة.behind a paywallيمكنك التحقق من ذلك تقنيًا من خلاللعبة iTunes(24.99 دولار سنويا)فقط تخزين مكالمات AAC 256-kbps عبر الإنترنت؛ لا يزال ملفاتك الأصلية في وضع ما إذا كنت تختار استبدالها على جهاز Mac الحديث، يمكنك القيام بذلك في تطبيق الموسيقى.

لعبة iTunes

فجأة، بسبب عدم وجود خيارات، أذهب إلىbuilder routeإذا حصلت على جهاز كمبيوتر (iPhone في هذه الحالة) ، ما الذي يمنعني من بناء ما تحتاجه فقط مع الكود لإستخدامها؟ في هذه المقالة ، أريد مشاركة رحلتي الكاملة من الانزعاج نحو إنشاء وظيفة لاعب الموسيقى الأساسية: تحميل ملفات الصوت ، وتنظيم وتلعبها مرة أخرى ، ولكن في أغلب الأحيان ، أريد أن أذكر نفسي ،هذا لا يزال جهاز الكمبيوتر العملي، يجب أن أكون قادرا على جعلها تفعل ما أريد.

ما يقدم Apple (وآخرون) اليوم

قبل كتابة التطبيق الخاص بي ، بحثت عن الخيارات الرسمية والأطراف الثالثة لعب الموسيقى خارج الإنترنت.

تطبيقات Apple Built-in

Apple تتيح لك تقسيم الموسيقى مباشرة من iCloud عبر التطبيق الملفات ، ولكن وظيفتها ليست مصممة للمشاهدة الموسيقية.lacks essential featuresمثل إدارة قائمة التردد، والتصنيع عن البيانات الممتازة، أو سلاسل التردد، على الرغم من أنها تدعم التردد في الموسيقى، فإنها محدودة جداً.لم تكن تجربة المستخدم جيدة.

لم تكن تجربة المستخدم جيدة

تطبيقات طرف ثالث

ذهبت إلى متجر التطبيقات للبحث عن التطبيقات الرائعة التي تحل مشكلتي ، في حين أن هناك الكثير منها ، يعتمد الكثير علىsubscription-based pricing، نموذج مشكور لبرنامج يلعب فقط الملفات التي يتمتع بها المستخدمون بالفعل.دوبلرلقد لعب معها أثناء تجربة، ولكن UX يتم بناء على إدارة ألبومات. لم يكن البحث جيدًا، وأيضًا كان وظيفت إدخال من iCloud سريعًا وأكثر صعوبة لاستخدامها على عدد كبير من الملفات المملوكة.

Going Builder Mode: My Technical Journey (طريقة بناء: رحلة التقنية الخاصة بي)

مع ذلك، قررت إنشاء موسيقي مثالي الخاص بي الذي يلغي نقاط الألم:

  • البحث مرن بالكامل في كل ملفات iCloud ، بحيث يمكنني اختيار وتصدير ملف مع الموسيقى أو ملفات محددة بسرعة.
  • الوظيفة في إدارة الموسيقى على الأقل على النحو المناسب مع تطبيق الموسيقى الرسمي: الشقوق، وإدارة قائمة التعبير، والتصنيع على ألبومات، وما إلى ذلك.
  • رابط معزز و صديق

محاولة رد فعل الأرملة أولاً

قبل بضعة سنوات ، كنت أحب التكوين (يبدو أقرب إلى TypeScript) وتمتع بأمان الذاكرة مثل Rust ، ولكن دون الذاكرة الأصلية.async/awaitفي ذلك الوقت، كتابة الكود في وقت متأخر مقارنة مع Go أو JS / TS شعرت صعوبة وملابس طويلة.هذه التجربة أتركني مزعجًا، لذلك عندما قمت بإعادة النظر في هذا المشروع، كنت أتوجه في البداية إلى شيء أكثر علما.

وأوضح أنني ذهبت مع React Native أو Expo ، في أمل أن تستخدم تجربة تطوير الويب الخاصة بي وتدخل جهاز كمبيوتر مستخدم من الملفات الموجودة. إنشاء جهاز كمبيوتر مستخدم لمشاهدة كان بسيطًا ؛ هناك العديد من الأمثلة مفتوحة المصدر ومقاطع الفيديو التدريبية على بناء مستخدمي الموسيقى التي تبدو جيدة التي تناسب احتياجاتي.المشروع من قبل Gionatha Sturbaلأنه كان يبدو لديه كل الميزات التي أحتاجها لبرنامجي.

Attempting to build an app with React Native/Expo

الوصول إلى نظام الملفات وإدماج الملفات في الزوايا الشمسية تحطم المشاكل الرئيسية: المكتبات مثلexpo-filesystemيدعم اختيار الملفات الأساسية ، ولكن التهرب المفاجئ على مكتبات iCloud المرتبطة بشكل عميقoften failed or even caused app crashesهذا أدى إلى أن يكون واضحًا أنJavaScript-based approach introduced more complexityبدلا من العمل فقط مع APIات Apple الأصلية ، حتى لو كان هذا يعني خطوة تعلم أسرع.

يمنع iOS Sandboxing التطبيقات من قراءة الملفات دون إذن مستخدم واضح، مما يعني أن React Native لا يمكن الوصول إلى ملفات خارجية بشكل موثوق.

التبديل إلى SwiftUI

لقد ذهبت معSwiftUIبدلا من UIKit أو storyboards لأنني أريدclean and declarative UIالطول الذي سيبقى خارج الطريق في حين أنني ركزت على منطق الدبلوم ومشاركة البيانات مع الميزات الحديثة مثل async/await والتكامل معSwift Actors، وجدت أنه أسهل لإدارة تدفق البيانات والتوافق. SwiftUI أيضا أسهل بالتأكيد لتنظيم التطبيق إلى مكونات ViewModel الفردية ، مما ساعدني في الحصول على نتائج أفضل من LLMs مثل OpenAI o1 و DeepSeek.

تصميم App Architecture و Data Model

دعونا نذهب إلى المعمارية من التطبيقات التي خلقتها: استخدمت SQLite لتخزين البيانات المستمرة و اتجهت إلى المعمارية التطبيقية كأداة سرور بسيطة. اجتذبت CoreData لأنني بحاجة إلى السيطرة الصارمة على التخزين، الأسئلة العصبية، وخاصة البحث عن النص الكامل.

3 الشاشات الرئيسية

The app consists of 3 screen/modes:

  1. إدخال المكتبة. هذا هو مكان إضافة ملف المكتبة iCloud الخاص بك. يصف التطبيق كل ملف لملف صوتي ويضيف كل مسار إلى قاعدة بيانات SQLite. بهذه الطريقة، يمكنك الحصول على مرونة كاملة في البحث، إضافة ملفات، وملفات ثانوية. ملف الفوركس الأصلية من أبل هو صعب جدا؛ لا يمكنك اختيار ملفات متعددة التي كنت تبحث عن الكلمات الرئيسية ثم أيضا مجموعة من الملفات في واحدة فقط.
  2. إدارة المكتبة.هذا هو المكان الذي يمكنك إدارة الأغاني المضافة وتنظيم قوائم التعبير.في معظم الأحيان، أظهرت كيف فعلت أبل ذلك في تطبيق الموسيقى، وأنه كان جيدًا بما يكفي لمتطلباتي.
  3. هذا الجزء من التطبيق يتعامل مع إدارة الجانب (تكرار ، التفكير) ، وما إلى ذلك ، واللعب ، وقف ، والعديد من الوظائف السينمائية التالية.

يتم عرض إطارات حركة المرور المستخدمية البسيطة هنا:

User flow diagram

User flow in practice:عند بدء التطبيق مع مكتبة فارغة ، تقع على صفحة Sync ، مما يظهر على زر "إضافة مصدر iCloud" الكبير. اختار ملف هناك ، و يظهر شاشة Sync صفحة التقدم أثناء المشي على الشجرة. بمجرد الانتهاء من تسجيل الدخول ، يتم إرسالك إلى صفحة المكتبة ، التي تشمل قائمة الشاشة الأولىPlaylists / Artists / Albums / Songsانقر فوق أي قائمة، انقر فوق قطعة، وستظهر ميني لاعب على أقصى الجانب؛ انقر فوق هذه القطعة من أجل فتح المتصفح على الشاشة بأكملها مع تكرار، إعادة التقييم، الترتيب، والطاقة. انقر فوق أو انقر فوق الصورة المفتوحة، وسوف تذهب مباشرة إلى المكتبة أثناء التعبير. في أي وقت تحتاج إلى المزيد من الموسيقى، انقر فوق "+" في الشاشة، انقر فوق "+" في الشاشة، اختر ملف آخر، وخدمة التصدير تجمع الأغاني الجديدة في الخلفية، لا تحتاج إلى إعادة تشغيل.

Backend-Like لوحة منطقية

بعد أن كان لديك خلفية على شبكة الإنترنت / الشبكة الضوئية وتوفير الكثير من الكود أثناء العمل في الشركات الناشئة ، ذهبت معbackend-like architectureبالنسبة إلى التطبيق المحمول، تم تقسيم جميع المساحة / طبقة منطقية منView and View-Model layerلأنني بحاجة إلى إزالةcloud syncing, metadata parsingأسلوب التطبيق وتتمكن من الوصول إلى بيانات نظيفة إلى SQLite DB.إليك خريطة التخزين الممتازة التي استخدمت هنا:

Layered architecture diagram

How the layers talk:يقع SQLite في أسفل ، ويتم تخزين صفوف الأغاني الخضراء والمجلدات FTS. ثم يتم إزالة المجلدات في قاعدة البيانات وإظهار API async.domain actorsشركاء Swift الذين لديهم جميع القواعد التجارية (تصدير، البحث، منطق الجانب) حتى تظل التغيرات الحاليةthread-safeViewModels تتلقى الممثلين ، تحويل البيانات إلى هيكلات مستعدة لـ UI ، و SwiftUI تظهر فقط ما تحصل عليه.nicely decoupled.

تطبيق البحث عن النص الكامل مع SQLite

كما ذكرت سابقاً ، من المثير للاهتمام أن يمكنك استيراد نسخة SQLite مع إمكانات FTS: بدءاً من iOS 11 ، فإنه متاح خارج الصندوق.without extra setupهذا يجعل من السهل دمج البحث الفكري في مكتبة الموسيقى الخاصة بي.without any third-party dependenciesبالإضافة إلى ذلك، استخدمت مكتبة SQLite.swift للمتطلبات العادية (التي تعمل كوسيلة من نوعها لتصميم المتطلبات مع سلامة وقت الترجمة)، ومع ذلك، بالنسبة للمتطلبات FTS، كنت بحاجة إلى اتخاذ استفسارات SQL العادية.

سكوتياFTS5وقد تمكنت من البحث عن أسماء الملفات والبيانات الممتازة مثل الممثل واللبنات والأسم دون البنية التحتية إكسابية إضافية.

إعداد جدولات FTS

Domain

Swift actor / repo

FTS5 table

Columns that get indexed

Library songs

SQLiteSongRepository

songs_fts

artist, title, album, albumArtist

Source-browser paths

SQLiteSourcePathSearchRepository

source_paths_fts

fullPath, fileName

أغنية المكتبة

SQLiteSongRepository

songs_fts

artist،title،album،albumArtist

مصدر براءات الاختراع Paths

SQLiteSourcePathSearchRepository

source_paths_fts

fullPath،fileName

أود أن أشير إلى أننا نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع أن نستطيع.songs،source_pathsFTS هيread-only for the UIجميع النصائح تنتج داخل المخزونات حتى لا تصل أي شيء من خلال الشقوق.

إنشاء مؤشر البحث

FTS5 المدمج في SQLite يجعل البحث السريع سهلًا.

try db.execute("""
CREATE VIRTUAL TABLE IF NOT EXISTS songs_fts USING fts5(
  songId UNINDEXED,
  artist, title, album, albumArtist,
  tokenize='unicode61'
);
""")

لقد استخدمunicode61لضمان أن يتم التعامل مع مجموعة واسعة من العلامات.المصطلحات غير المرغوب فيهاUNINDEXEDلذلك ، لا تزداد معاناة المصطلح في الكلمات.

تحديث البيانات بشكل موثوق

للحفاظ على الأشياء بسيطة وآمنة ، قم بتجميع التحديثات وتدميرها في المعاملات ، وهذا يؤكد أن مؤشر البحث لا ينخفض أبداً ، حتى إذا تراجع التطبيق أو يتم إلغاءه.

func upsertSong(_ song: Song) async throws {
    db.transaction {
        // insert or update main song data
        // insert or update search index data
    }
}

البحث عن Fuzzy Search

لأفضل طريقة للبحث، أضيف دعم بطاقة غريبة تلقائياً.إذا قمت بتحميل "اللون" ، فإنه يبحث عن "اللون*" داخلياً ، مما يوفر نتائج على الفور حتى مع طلبات جزئية.

أيضًا، يُمكننا أن نستخدم تقنيات الذكاء الاصطناعي (bm25) للعودة إلى نتائج أكثر أهمية دون تعقيدات إضافية:

SELECT s.*
FROM songs s JOIN songs_fts fts ON s.id = fts.songId
WHERE songs_fts MATCH ?
ORDER BY bm25(songs_fts)
LIMIT ? OFFSET ?;

على سبيل المثال ، استخدمت SQLite الحمراء ليتمكن من الحصول على مرونة تحتاجها: التخطيط المتوقع ، الوصول المحلي أولاً ، والبحث الكامل القوي ، دون إدراج أي اتجاهات الشبكة أو خدمات خارجية.

العمل مع ملفات iOS و Bookmarks

على iOS ، يمكن لأجهزة التطبيقات تخزين علامات التخزين المستمرة لموقع الملف ، ولكنsecurity-scoped bookmarks، والتي تمنح الوصول الموسع إلى الملفات خارج غرفة الصخور في التطبيق ، متوفرة فقط علىmacOSقد تستخدم تطبيقات iOS علامات المفاتيح المعتادة لتذكر مسارات الملفات وتطلب الوصول مرة أخرى من خلال خيار الدردشة، ولكن لا يضمن هذا الوصول أن يستمر في الصمت.مستندات Bookmark Apple.

لتقليل هذا، لقد وضعت آلية إعادة التأهيل التي يتم نسخ الملفات إلىapp's own sandboxed containerوهذا يؤدي إلى تجنب دورة حياة المفاتيح المفروضة على الأمان التي يمكن أن تنتهي بشدة إذا استمرت iOS في إعادة الترخيص إلى الحقوق.على سبيل المثال، من خلال نسخ الملفات بشكل فعال في الخلفية، في حين أن المفاتيح حقيقية، لا يوجد خطر في الوصول إلى إشارات ملفات الصوت غير صحيح.

هذا النهج يسهل أيضًا زيادة سرعة تسجيل الملفات، ويمكنني مراجعة هيكل الملفات مرة واحدة (عندما يكون الوصول فعالًا)، إدخال ملفات الصوت ذات الصلة فقط، وإرسال ملفات الصوت بشكل آمن عبر الملفات المملوكة عميقًا.لا يزال مشكلة غير مسبوقة ليوهذا يؤكد كيفunder-supportedهذه الحالة الاستخدامية هي ، حتى بالنسبة إلى التطبيقات الأصلية ، وكيفية تعقيدها لا تزالhandle file access reliably on iOS.

بناء Playback و UI

ميتاتيديا Parsing

لتحديث الملفات من الملفات الصوتية ، استخدمت أبلAVFoundation frameworkوخاصةً فيAVURLAssetالفئة، والتي تسمح للتحقق من بيانات الملفات المتعددة، مثل عنوان، الفنان الألبوم، وما إلى ذلك في حين تحليل الملفات المتعددة يتم معالجتها من قبل SDK الأصلية، بعض المجالات مثل أرقام المرور لديك للتحقق من تقييمات ID3 يدويًا.البحث عن GitHubالبحث عن أمثلة، لأن الوثائق الرسمية لم تكن متوافقة مع الحالات الجانبية.

إرسال صوت مع AVFoundation

بعد تصفية المكتبة ، يبدو تنفيذ لاعب صوتي بسيطًا جدًا: تحتاج فقط إلى تصفية عينات منAVAudioPlayerبالإضافة إلى ذلك، لميزات نوعية الحياة: لعب الموسيقى من مركز التحكم، كنت بحاجة إلى تطبيقAVAudioPlayerDelegateالبروتوكول وأيضًا معزولة في AppleMPRemoteCommandCenterويسمح للمطورين بالرد على أدوات التشغيل على المستوى النظام.

التفكير: Apple, Developer Lock-In, و المستقبل

إليك ما حدث خلال تطويرها:

الخطيئة

Xcode's limitations remain frustrating.إن إصدارات SwiftUI في الوقت الحقيقي هي بالتأكيد خطوة إلى الأمام، ولكن تجربة التنمية بشكل عام لا تزال غير متوافقة مع ما أعلنته Flutter قبل خمس سنوات: دمج VSCode قوي، إعادة تحميل المحاكاة في الوقت الحقيقي، وأدوات التشفير المعروفة.

Lack of editor flexibility.تحديد دعم بروتوكول سرور اللغات (LSP) لـ Swift في Neovim أو VSCode يتطلب أدوات إضافية مثل:xcode-build-serverو لا يزال لا يتوافق تماما مع تجربة المطورين من بيئات الإنترنت الأولى.

Some corners of Apple's SDK still live in Objective-C land.البحث عن ملف Spotlight ، على سبيل المثال ، يتم عرضها فقط من خلالNSMetadataQuery، الذي يستخدم Key-Value Observing (KVO) و String Keys ، لا يوجد أي ملحمة صديقة للسرعة حتى الآن.

SwiftUI's declarative UI is great, but debugging iCloud interactions still requires manual mocks.لا يمكن رؤية SwiftUI المفاجئة لتشكيل التطبيقات الكاملة التي تشمل حقول iCloud ، لذلك تحتاج إلى تجميد التفاعلات في الزاوية بشكل رئيسي ، وهو إزعاج صغير ولكن ملموس.

الجيد

Async/await.في النهاية ، يمكنني كتابة I / O-bound كود متوازن كويتي كاملاً بدون مكالمة مكالمة مشبوهة ، وهذا فوز كبير ، وأنا أعرف بشكل كبير كم سهل هو كتابة أيضًا كود متوازن إلى الممثلين ويسميه كما تفعل في بيئات جاكوارت.

Plethora of native libs.نعم، أنت لا تقتصر على الارتباطات المفتوحة مثل في بيئات React Native/Flutter. هنا لديك المزيد من الحرية في تطوير شيء "أكثر خطورة" من استبدال موقع ويب الشركة / المنتج الخاص بك (لأن تجربة الهواتف الذكية الأولى ضعيفة).

SwiftUIنعم ، فإن نهج React لتصنيع UI يمنح المزيد من الإنتاجية والمكان للبحث.

التالي: البناء يجب أن يكون أسهل

بعد أسبوعين ونصف من الهجمات ، تمكنت من الحصول على قطعة من البرمجيات التي تلبي احتياجاتي بالضبط:local/offline music playerيمكنك إدخال ملفات الصوت من محفظة الضوء.

ولكن المطورين يدركون بسرعة أنهم لا يستطيعون بسهولة تطوير التطبيقات على أجهزتهم في هذه الأيام ويخافون من ذلك: التطبيقات تعمل فقط7 أيام دون شهادة Devو بعد ذلك ، يجب عليك إعادة بناءها ، ما لم تشتري 99 دولار إلى أبل للتسجيل في برنامج التطوير.

7 أيام دون شهادة Dev

حتى بعد أنDMA Act in the EUلا يزال المستخدمين في الاتحاد الأوروبي يمكنهم الآن تثبيت التطبيقات من الأسواق الخارجية مباشرة من موقع المطور، ولكن فقط إذا كان هذا المطور لا يزال مستأجرًا في برنامج Apple $ 99 / عام وتوافق مع شروط Apple بديلة.

هذا لا يعني في نهاية المطاف.شركة تكنولوجيا مبتكرة تضع نشاطا في تطوير التطبيقات الديموقراطية. حتى تطبيقات الويب المتطورة (PWAs)مواجهة الحد الأدنى على iOS: حتى بعد تحديثات أبل 16-18.x ، لا تزال PWA iOS تعمل داخل غرفة صغيرة من سامسونج. إنها تحصل على WebGL2 و web-push ، ولكنها لا تحصل على Web Bluetooth / USB / NFC ، Background Sync ، أو أكثر من ~50MB من الامتياز المضمنة. WebGL يعمل من خلال Metal shim ، لذلك معدل المراحل في العالم الحقيقي غالباً ما تتبع تطبيقات Metal الأصلية ؛ وهذا جيد بما فيه الكفاية لـ UI ، ولكن ليس لألعاب AAA 3D.

في الوقت الحاضر، تم تقليل تعقيد تطوير البرمجيات الحديثة من خلال السماح لأي شخص بالتعامل مع التكنولوجيات غير المعروفة عن طريق توفير كل المعرفة اللازمة بطريقة قابلة للتطبيق. يمكنك أن ترى بشكل واضح كيف أصبح تطوير الويب أكثر اهتمامًا من الأشخاص غير التقنيين الذين لديهم طريقة لبناء أفكارهم دون التخصص في العديد من التكنولوجيات.حتى لو كنت تخطط لنفسك ، فإن Apple لا يزال يحصل على الكلام النهائي.قبل أن تتمكن من القيام بذلك لفترة أطول من أسبوع.tight restrictions that hinder personal app developmentوقد جعلت AI أسهل من أي وقت مضى من إنشاء أدوات جديدة ، ما لم تكن تعمل على إنشاء iOS ، حيث لا تزال البوابة مغلقة.

اليمين المرتبطة

  • iTunes Match - دعم Apple
  • اكسسوارات إلكترونية – Apple Docs
  • FTS5 - توثيق SQLite
  • أندرويد Music Player - App Store
  • برنامج EXPO FileSystem
  • معلومات برنامج Apple Developer (7 يومًا)
  • Apple Community: Files App و MP3 Playback


L O A D I N G
. . . comments & more!

About Author

Oleg Pustovit HackerNoon profile picture
Oleg Pustovit@nexo-tech
Startup tech lead with a focus on DevOps, automation, and lean MVP development. Sharing insights from building early-stage products and platforms.

شنق العلامات

تم تقديم هذه المقالة في...

Trending Topics

blockchaincryptocurrencyhackernoon-top-storyprogrammingsoftware-developmenttechnologystartuphackernoon-booksBitcoinbooks