Bezdepbonusu7Программирование: статьи и ответы

Вопрос

Seaside: CannotDeleteFileException: не удалось удалить старую версию топливного файла

Автор вопроса: Jayalakshmi LadeОтветов: 2

В приложении pharo seaside при нажатии кнопки "Домой" все данные будут сохранены в топливном файле с некоторым именем класса как Test.fl. Если я вызываю одну и ту же домашнюю страницу одновременно в двух экземплярах, оба вызывают этот код ниже, чтобы сохранить файл Test.fl с последними обновлениями,

FLSerializer
    serialize: self allObjects
    toFileNamed: self name , '.fl'**

и получение исключения:

CannotDeleteFileException: не удалось удалить старую версию файла ...\Pharo3.0\Test.fl

И я использовал Mutex, чтобы разрешить выполнение другого экземпляра после первого экземпляра,

mutexBlock := Mutex new.
mutexBlock critical: [
    FLSerializer
        serialize: self allObjects
        toFileNamed: self name , '.fl' ]

Но все же я получаю ту же ошибку

CannotDeleteFileException: не удалось удалить старую версию файла

Пожалуйста, помогите мне в этом, чтобы исправить ошибку.

smalltalkseasidepharo

Ответы

Ответ 1 · рейтинг 5 · Max Leske

Вероятно, ваша интуиция верна: два процесса одновременно пытаются записать (удалить) один и тот же файл. Однако ваш подход Mutex не будет работать, потому что вы создаете новый Mutex каждый раз, когда выполняете этот код. Вы должны хранить Mutex в переменной класса или экземпляра (в зависимости от того, как работает ваш код), чтобы каждый процесс использовал один и тот же экземпляр Mutex.

Тогда ваш код будет выглядеть примерно так:

MyClass class>>serializeProtect
    ^ SerializeProtect ifNil: [ SerializeProtect := Mutex new ]

self class serializeProtect critical: [
    FLSerializer
        serialize: self allObjects
        toFileNamed: self name , '.fl' ]

Примечание: обычно не лениво инициализировать Mutex. Я просто делаю это здесь для простоты.

Ответ 2 · Stephan Eggermont

Вам не нужен мьютекс там. Seaside в Pharo обрабатывает запросы по одному. То есть это работает только в том случае, если ваша запись файла выполняется быстро, так как все остальные соединения ждут завершения записи. Если это не так, вам нужно будет писать в отдельном потоке, а затем действительно контролировать доступ к нему.

Перевод вопроса и ответов сообщества Stack Overflow, лицензия CC BY-SA. Оригинал на Stack Overflow.

Похожие материалы