Gogs 3 săptămâni în urmă
părinte
comite
94df25d5c1
2 a modificat fișierele cu 245 adăugiri și 268 ștergeri
  1. 6 5
      README.md
  2. 239 263
      scripts/seed-events.coffee

+ 6 - 5
README.md

@@ -1,9 +1,10 @@
 # Текущая ззадача
-Провести полный рефакторинг кода.
-убрать EventBus так как он не работает,
-для работы с модальными окнати использовать _.modalState
-доработать страницу Events (доработать фильты, изменить дизайн сделать 2-3 колонки в десктопе), Сделать открытие /events/[id мероприятия]
-с главной странице убираем фильтры, и выводим минимум 6 анонсов
+доработай seed-events.coffee, так что бы он проверял наличие базы данных.
+создай _desing документы с необходимым набором view/map функций, _desing документ сделай отдельным файлом, весь код на coffeescript
+ля взаимодействия с couchdb используй pouchdb.
+скрипт должен проверять их наличие и соответствие текущей версии, и если их нет то создавать или обновлять.
+описать структуру хранимых данных и интерфейсы доступа к ним. (общий объект "запись блога", наследующие её структуру "слайд" и "мероприятие"
+основной текст, пишется на markdown. 
 
 # применяй правила:
 

+ 239 - 263
scripts/seed-events.coffee

@@ -1,270 +1,246 @@
-#!/usr/bin/env coffee
-
-# Скрипт для добавления тестовых мероприятий в CouchDB
-
+# Подключение необходимых модулей
+CouchDB = require '../vue/app/core/CouchdbClass.coffee'
+debug = require('../../../utils/coffee/debug.coffee').default
 class EventSeeder
-  constructor: ->
-    @baseUrl = 'http://localhost:5984'
-    @dbName = 'kohi_borbad_events'
-    @headers = 
-      'Content-Type': 'application/json'
-      'Authorization': 'Basic ' + Buffer.from('oleg:631074').toString('base64')
+    constructor: ->
+        @dbName = 'borbad_events'
+        @baseUrl = 'http://oleg:631074@localhost:5984'
+        @couch = new CouchDB(@baseUrl, @dbName)
+        @designDoc = 
+            _id: '_design/app'
+            views: {}
+            lists: {}
+            shows: {}
+        
+        # Версия design документа для контроля обновлений
+        @designVersion = '1.0'
     
-    # Тестовые мероприятия
-    @testEvents = [
-      {
-        _id: 'event_classical_001'
-        title: 'Концерт симфонического оркестра'
-        date: '2025-10-15'
-        time: '19:00'
-        description: 'Произведения Чайковского и Рахманинова в исполнении Национального симфонического оркестра под руководством маэстро Фирдавса Абдурахмонова. Незабываемый вечер классической музыки в акустике мирового уровня.'
-        shortDescription: 'Шедевры классической музыки в исполнении Национального симфонического оркестра'
-        image: '/images/event-classical.jpg'
-        category: 'classical'
-        price: 50
-        venue: 'Большой зал'
-        duration: '2 часа 30 минут'
-        ageRestriction: '12+'
-        availableTickets: 45
-        isFeatured: true
-        inSlider: true
-        cta: 'Купить билеты'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_folk_001'
-        title: 'Вечер таджикской народной музыки'
-        date: '2025-10-20'
-        time: '18:30'
-        description: 'Выступление фольклорного ансамбля "Шашмаком" с программой традиционных мелодий и танцев. Погрузитесь в богатую культурную традицию Таджикистана через музыку, песни и танцы.'
-        shortDescription: 'Традиционные мелодии и танцы Таджикистана'
-        image: '/images/event-folk.jpg'
-        category: 'folk'
-        price: 30
-        venue: 'Малый зал'
-        duration: '2 часа'
-        ageRestriction: '6+'
-        availableTickets: 28
-        isFeatured: true
-        inSlider: true
-        cta: 'Узнать больше'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_jazz_001'
-        title: 'Джазовый фестиваль "Borbad Jazz"'
-        date: '2025-10-25'
-        time: '20:00'
-        description: 'Международные джазовые коллективы из Европы и Азии в уникальной акустике зала. Три дня незабываемой музыки от лучших джазменов мира. От традиционного джаза до современных экспериментов.'
-        shortDescription: 'Международные джазовые коллективы'
-        image: '/images/event-jazz.jpg'
-        category: 'jazz'
-        price: 70
-        venue: 'Большой зал'
-        duration: '3 часа'
-        ageRestriction: '16+'
-        availableTickets: 15
-        isFeatured: true
-        inSlider: true
-        cta: 'Смотреть расписание'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_pop_001'
-        title: 'Концерт популярной музыки'
-        date: '2025-10-28'
-        time: '19:30'
-        description: 'Лучшие поп-исполнители Таджикистана представят новые хиты и классические композиции. Энергичное шоу с современной хореографией и световыми эффектами.'
-        shortDescription: 'Лучшие поп-исполнители страны'
-        image: '/images/event-pop.jpg'
-        category: 'pop'
-        price: 45
-        venue: 'Большой зал'
-        duration: '2 часа 15 минут'
-        ageRestriction: '12+'
-        availableTickets: 67
-        isFeatured: true
-        inSlider: false
-        cta: 'Купить билеты'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_opera_001'
-        title: 'Оперный гала-концерт'
-        date: '2025-11-02'
-        time: '18:00'
-        description: 'Известные оперные певцы исполнят арии из мировых шедевров оперного искусства. Вечер великой музыки в исполнении мастеров оперной сцены.'
-        shortDescription: 'Арии из мировых оперных шедевров'
-        image: '/images/event-opera.jpg'
-        category: 'classical'
-        price: 80
-        venue: 'Большой зал'
-        duration: '2 часа 45 минут'
-        ageRestriction: '12+'
-        availableTickets: 23
-        isFeatured: false
-        inSlider: false
-        cta: 'Забронировать места'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_dance_001'
-        title: 'Танцевальное шоу "Восточные ритмы"'
-        date: '2025-11-05'
-        time: '19:00'
-        description: 'Традиционные и современные танцевальные коллективы представят красочное шоу. Яркие костюмы, зажигательная музыка и мастерство танцовщиков со всего Таджикистана.'
-        shortDescription: 'Традиционные и современные танцы'
-        image: '/images/event-dance.jpg'
-        category: 'dance'
-        price: 35
-        venue: 'Большой зал'
-        duration: '2 часа 30 минут'
-        ageRestriction: '6+'
-        availableTickets: 89
-        isFeatured: true
-        inSlider: true
-        cta: 'Посмотреть программу'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_chamber_001'
-        title: 'Камерная музыка: Струнный квартет'
-        date: '2025-11-08'
-        time: '17:00'
-        description: 'Изысканная программа камерной музыки в исполнении ведущего струнного квартета страны. Интимная атмосфера и тонкое звучание в акустике камерного зала.'
-        shortDescription: 'Изысканная камерная музыка'
-        image: '/images/event-chamber.jpg'
-        category: 'classical'
-        price: 40
-        venue: 'Камерный зал'
-        duration: '1 час 45 минут'
-        ageRestriction: '12+'
-        availableTickets: 34
-        isFeatured: false
-        inSlider: false
-        cta: 'Приобрести билеты'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-      {
-        _id: 'event_experimental_001'
-        title: 'Фестиваль современной музыки'
-        date: '2025-11-12'
-        time: '20:30'
-        description: 'Экспериментальные проекты и инновационные музыкальные направления. Откройте для себя новые грани музыкального искусства от молодых композиторов и исполнителей.'
-        shortDescription: 'Экспериментальные музыкальные проекты'
-        image: '/images/event-modern.jpg'
-        category: 'experimental'
-        price: 55
-        venue: 'Малый зал'
-        duration: '3 часа'
-        ageRestriction: '18+'
-        availableTickets: 18
-        isFeatured: false
-        inSlider: true
-        cta: 'Исследовать программу'
-        createdAt: new Date().toISOString()
-        updatedAt: new Date().toISOString()
-      }
-    ]
-
-  # Проверить существование базы данных
-  checkDatabase: ->
-    try
-      response = await fetch("#{@baseUrl}/#{@dbName}", {
-        method: 'GET'
-        headers: @headers
-      })
-      
-      if response.ok
-        console.log '✅ База данных существует'
-        return true
-      else if response.status == 404
-        console.log '📁 База данных не существует, создаем...'
-        return await this.createDatabase()
-      else
-        console.error '❌ Ошибка проверки базы данных:', response.statusText
-        return false
-    catch error
-      console.error '❌ Ошибка подключения к CouchDB:', error.message
-      return false
-
-  # Создать базу данных
-  createDatabase: ->
-    try
-      response = await fetch("#{@baseUrl}/#{@dbName}", {
-        method: 'PUT'
-        headers: @headers
-      })
-      
-      if response.ok
-        console.log '✅ База данных создана успешно'
-        return true
-      else
-        console.error '❌ Ошибка создания базы данных:', response.statusText
-        return false
-    catch error
-      console.error '❌ Ошибка создания базы данных:', error.message
-      return false
-
-  # Добавить мероприятие
-  addEvent: (event) ->
-    try
-      response = await fetch("#{@baseUrl}/#{@dbName}/#{event._id}", {
-        method: 'PUT'
-        headers: @headers
-        body: JSON.stringify(event)
-      })
-      
-      if response.ok
-        result = await response.json()
-        console.log "✅ Мероприятие добавлено: #{event.title}"
-        return { success: true, id: result.id }
-      else
-        console.error "❌ Ошибка добавления мероприятия #{event.title}:", response.statusText
-        return { success: false, error: response.statusText }
-    catch error
-      console.error "❌ Ошибка добавления мероприятия #{event.title}:", error.message
-      return { success: false, error: error.message }
-
-  # Основная функция заполнения базы
-  seed: ->
-    console.log '🎭 Начало заполнения базы данных мероприятиями...'
+    # Проверка существования базы данных
+    checkDatabase: ->
+        try
+            response = await fetch(@baseUrl+"/"+@dbName)
+            if response.status == 404
+                debug.log "База данных не найдена, создаем новую"
+                await this.createDatabase()
+            else if response.status == 200
+                debug.log "База данных найдена"
+            else
+                debug.log "Ошибка при проверке базы: "+response.status
+        catch error
+            debug.log "Ошибка при проверке базы данных: "+error
+    
+    # Создание базы данных
+    createDatabase: ->
+        try
+            response = await fetch(@baseUrl+"/"+@dbName, 
+                method: 'PUT'
+                headers: 
+                    'Content-Type': 'application/json'
+            )
+            if response.status == 201
+                debug.log "База данных успешно создана"
+            else
+                debug.log "Ошибка при создании базы: "+response.status
+        catch error
+            debug.log "Ошибка при создании базы данных: "+error
     
-    # Проверяем базу данных
-    databaseExists = await this.checkDatabase()
-    if not databaseExists
-      console.log '❌ Не удалось подключиться к базе данных'
-      process.exit(1)
+    # Проверка и создание/обновление design документов
+    setupDesignDocuments: ->
+        try
+            # Получаем текущий design документ
+            response = await fetch(@baseUrl+"/"+@dbName+"/_design/app")
+            
+            if response.status == 200
+                existingDoc = await response.json()
+                # Проверяем версию
+                if existingDoc.version != @designVersion
+                    debug.log "Обновляем design документ до версии "+@designVersion
+                    @designDoc._rev = existingDoc._rev
+                    @designDoc.version = @designVersion
+                    await this.updateDesignDoc()
+                else
+                    debug.log "Design документ актуален"
+            else if response.status == 404
+                debug.log "Design документ не найден, создаем новый"
+                @designDoc.version = @designVersion
+                await this.createDesignDoc()
+            else
+                debug.log "Ошибка при проверке design документа: "+response.status
+                
+        catch error
+            debug.log "Ошибка при настройке design документов: "+error
     
-    # Добавляем мероприятия
-    successCount = 0
-    for event in @testEvents
-      result = await this.addEvent(event)
-      if result.success
-        successCount += 1
-      # Небольшая задержка между запросами
-      await new Promise (resolve) -> setTimeout resolve, 100
+    # Создание design документа
+    createDesignDoc: ->
+        try
+            # Определяем views
+            @designDoc.views =
+                # Все записи блога
+                all_blog_posts:
+                    map: """
+                    function(doc) {
+                        if (doc.type === 'blog_post' || doc.type === 'slide' || doc.type === 'event') {
+                            emit(doc.created_at, doc);
+                        }
+                    }
+                    """
+                
+                # Только мероприятия
+                events_only:
+                    map: """
+                    function(doc) {
+                        if (doc.type === 'event') {
+                            emit(doc.event_date, doc);
+                        }
+                    }
+                    """
+                
+                # Только слайды
+                slides_only:
+                    map: """
+                    function(doc) {
+                        if (doc.type === 'slide') {
+                            emit(doc.order, doc);
+                        }
+                    }
+                    """
+                
+                # Поиск по заголовку
+                by_title:
+                    map: """
+                    function(doc) {
+                        if (doc.title) {
+                            emit(doc.title.toLowerCase(), doc);
+                        }
+                    }
+                    """
+                
+                # Поиск по тегам
+                by_tags:
+                    map: """
+                    function(doc) {
+                        if (doc.tags && Array.isArray(doc.tags)) {
+                            doc.tags.forEach(function(tag) {
+                                emit(tag.toLowerCase(), doc);
+                            });
+                        }
+                    }
+                    """
+                
+                # Активные мероприятия (будущие)
+                active_events:
+                    map: """
+                    function(doc) {
+                        if (doc.type === 'event' && doc.event_date) {
+                            var eventDate = new Date(doc.event_date);
+                            var now = new Date();
+                            if (eventDate >= now) {
+                                emit(doc.event_date, doc);
+                            }
+                        }
+                    }
+                    """
+            
+            response = await fetch(@baseUrl+"/"+@dbName+"/_design/app",
+                method: 'PUT'
+                headers: 
+                    'Content-Type': 'application/json'
+                body: JSON.stringify(@designDoc)
+            )
+            
+            if response.status == 201
+                debug.log "Design документ успешно создан"
+            else
+                debug.log "Ошибка при создании design документа: "+response.status
+                
+        catch error
+            debug.log "Ошибка при создании design документа: "+error
     
-    console.log "\n🎉 Заполнение завершено!"
-    console.log "✅ Успешно добавлено: #{successCount} из #{@testEvents.length} мероприятий"
+    # Обновление design документа
+    updateDesignDoc: ->
+        try
+            response = await fetch(@baseUrl+"/"+@dbName+"/_design/app",
+                method: 'PUT'
+                headers: 
+                    'Content-Type': 'application/json'
+                body: JSON.stringify(@designDoc)
+            )
+            
+            if response.status == 201
+                debug.log "Design документ успешно обновлен"
+            else
+                debug.log "Ошибка при обновлении design документа: "+response.status
+                
+        catch error
+            debug.log "Ошибка при обновлении design документа: "+error
     
-    if successCount == @testEvents.length
-      console.log '🎊 Все мероприятия успешно добавлены в базу данных!'
-    else
-      console.log '⚠️  Некоторые мероприятия не были добавлены'
+    # Добавление тестовых данных
+    seedTestData: ->
+        testData = [
+            {
+                _id: 'slide_welcome'
+                type: 'slide'
+                title: 'Добро пожаловать в Кохи Борбад'
+                content: '# Концертный зал Борбад\n\nПриветствуем вас в самом современном концертном зале Душанбе!'
+                image: '/assets/borbad.s5l.ru/welcome-slide.jpg'
+                order: 1
+                active: true
+                created_at: new Date().toISOString()
+                updated_at: new Date().toISOString()
+            }
+            {
+                _id: 'event_concert_1'
+                type: 'event'
+                title: 'Симфонический оркестр'
+                content: '## Концерт симфонического оркестра\n\nВ программе произведения классической музыки.'
+                event_date: new Date(Date.now() + 7 * 24 * 60 * 60 * 1000).toISOString()
+                location: 'Большой зал'
+                price: 150
+                tags: ['концерт', 'классика', 'оркестр']
+                image: '/assets/borbad.s5l.ru/concert-1.jpg'
+                created_at: new Date().toISOString()
+                updated_at: new Date().toISOString()
+            }
+            {
+                _id: 'blog_about'
+                type: 'blog_post'
+                title: 'О нашем зале'
+                content: '## История создания\n\nКонцертный зал Борбад был открыт в 2023 году...'
+                tags: ['история', 'архитектура']
+                created_at: new Date().toISOString()
+                updated_at: new Date().toISOString()
+            }
+        ]
+        
+        for doc in testData
+            try
+                response = await fetch(@baseUrl+"/"+@dbName+"/"+doc._id,
+                    method: 'PUT'
+                    headers: 
+                        'Content-Type': 'application/json'
+                    body: JSON.stringify(doc)
+                )
+                
+                if response.status == 201
+                    debug.log "Документ "+doc._id+" успешно создан"
+                else
+                    debug.log "Ошибка при создании документа "+doc._id+": "+response.status
+                    
+            catch error
+                debug.log "Ошибка при создании тестового документа: "+error
+    
+    # Основной метод инициализации
+    initialize: ->
+        debug.log "Начало инициализации базы данных мероприятий"
+        await this.checkDatabase()
+        await this.setupDesignDocuments()
+        await this.seedTestData()
+        debug.log "Инициализация базы данных завершена"
+
+# Экспорт класса
+module.exports = EventSeeder
 
-# Запуск скрипта
-seeder = new EventSeeder()
-seeder.seed().then ->
-  console.log '\n✨ Скрипт завершил работу'
-  process.exit(0)
-.catch (error) ->
-  console.error '\n💥 Критическая ошибка:', error
-  process.exit(1)
+# Если файл запускается напрямую
+if require.main == module
+    seeder = new EventSeeder()
+    seeder.initialize()