Я пытаюсь попрактиковаться с хранилищем данных GAE, чтобы получить представление о механизмах запросов и выставления счетов.
Я прочитал книгу Орейли о GAE и посмотрел видео Google о хранилище данных.Моя проблема в том, что лучшие методы обычно касаются большего числа операций чтения, чем записи в хранилище данных.
Я создал супер простое приложение:
- существует две веб-страницы - одна для выбора ссылоки одним просмотром выбранных ссылок
- каждый пользователь может выбрать добавление URL-ссылок в свой «канал ссылок»
- . Пользователь может выбрать столько ссылок, сколько он хочет, в любое время.
- на другой веб-странице, я хочу показать пользователю самые последние 10 ссылок, которые он выбрал.
- каждый пользователь имеет свою собственную веб-страницу "ссылок".
- на каждой "ссылке"Я хочу сохранить и показать некоторые метаданные - например: сама ссылка URL;когда это было выбрано;сколько раз оно уже появилось в ленте;и т. д.
В этом случае, поскольку пользователь может выбрать столько ссылок, сколько он хочет, мое приложение записывает в хранилище данных намного больше, чем количество операций чтения (запись - когда пользовательвыбрал другую ссылку, прочитайте - когда пользователь открывает веб-страницу, чтобы увидеть свой «канал ссылок»)
Вопрос 1: Я могу придумать (как минимум) два варианта, как обрабатывать данныедля этого приложения:
Вариант A: - сохранить объект на пользователя с данными пользователя, регистрацией и т. д. - сохранить другой объект на пользователя, который содержит его последние 10 выбранных ссылок, которые будут отображатьсяна веб-страницу пользователя после того, как он ее запросит
Опция B: - сохранить объект на ссылку URL - это означает, что все URL всех пользователей будут сохранены как один и тот же объект - сохранить объект наданные пользователя (такие же, как в варианте A), но добавьте ссылку на URL пользователя в большую таблицу URL
Какой метод будет лучше?
Вопрос 2: Если я хочу посчитатьобщее количество URL-адресов, выбранных до сегодняшнего дня, или ежедневное количество URL-адресов, которые выбрал пользователь, или любой другой счет - должен ли я использовать его с моими инструментами SDK или я должен вставить счетчики в сущности, которые я описал выше?(Я хочу максимально уменьшить количество записей в хранилище данных)
РЕДАКТИРОВАТЬ (чтобы ответить на комментарий @ Elad): Предположим, я хочу сохранить только 10 последних URL-адресов для пользователей.от остальных я хочу избавиться (чтобы не перенаселять мою БД ненужными данными).
РЕДАКТИРОВАТЬ 2: после добавления кода Итак, я сделал попытку с помощью следующего кода (пробуя сначала метод Элада):
Вот мой класс:
class UserChannel(db.Model):
currentUser = db.UserProperty()
userCount = db.IntegerProperty(default=0)
currentList = db.StringListProperty() #holds the last 20-30 urls
Затем я сериализовал URL-адрес и метаданные в строки JSON, которые пользователь отправляет с первой страницы.Вот как обрабатывается POST:
def post(self):
user = users.get_current_user()
if user:
logging messages for debugging
self.response.headers['Content-Type'] = 'text/html'
#self.response.out.write('<p>the user_id is: %s</p>' % user.user_id())
updating the new item that user adds
current_user = UserChannel.get_by_key_name(user.nickname())
dataJson = self.request.get('dataJson')
#self.response.out.write('<p>the dataJson is: %s</p>' % dataJson)
current_user.currentPlaylist.append(dataJson)
sizePlaylist= len(current_user.currentPlaylist)
self.response.out.write('<p>size of currentplaylist is: %s</p>' % sizePlaylist)
#whenever the list gets to 30 I cut it to be 20 long
if sizePlaylist > 30:
for i in range (0,9):
current_user.currentPlaylist.pop(i)
current_user.userCount +=1
current_user.put()
Updater().send_update(dataJson)
else:
self.response.headers['Content-Type'] = 'text/html'
self.response.out.write('user_not_logged_in')
где Updater - это мой метод обновления через Channel-API веб-страницы с помощью канала.
Теперь все работает, я вижу каждого пользователя.имеет ListProperty с 20-30 ссылками (когда он достигает 30, я сократил его до 20 с помощью pop ()), но!цены довольно высоки ... каждый POST, такой как здесь, занимает ~ 200 мс, 121 cpu_ms, cpm_usd = 0,003588.Это очень дорого, учитывая все, что я делаю, это сохраняю строку в списке ... Думаю, проблема может заключаться в том, что сущность становится большой с большим ListProperty?