Fix UUID subscriptable error and improve Monero account creation
- Fix crypto_processor.py UUID slicing error by using shop.uuid_str
- Use clean UUID-based label: mps-shop-{uuid}
- Add account tagging with shop name for human identification
- Update development.ini to use environment variables for payment toggles
- Run black formatter on all Python files
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
parent
2a89b94a29
commit
3f23b7eea8
57 changed files with 1172 additions and 797 deletions
|
|
@ -65,8 +65,8 @@ app.bucket.secure_uploads.secret_key = ${MPS_APP_SECURE_UPLOADS_SECRET_KEY}
|
|||
app.stripe.test_mode = True
|
||||
|
||||
# Payment method toggles
|
||||
app.payments.stripe.enabled = True
|
||||
app.payments.monero.enabled = False
|
||||
app.payments.stripe.enabled = ${MPS_PAYMENTS_STRIPE_ENABLED:-True}
|
||||
app.payments.monero.enabled = ${MPS_PAYMENTS_MONERO_ENABLED:-False}
|
||||
|
||||
# Monero RPC Configuration
|
||||
# RPC endpoint of monero-wallet-rpc (recommend binding to localhost only)
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@ import dkim
|
|||
import smtplib
|
||||
from email.mime.multipart import MIMEMultipart
|
||||
from email.mime.text import MIMEText
|
||||
|
||||
# Catch socket errors when postfix isn't running...
|
||||
from socket import error as socket_error
|
||||
import logging
|
||||
|
|
|
|||
|
|
@ -187,7 +187,9 @@ def main():
|
|||
.first()
|
||||
)
|
||||
if not xmr_processor or not xmr_processor.sweep_to_address:
|
||||
logger.error(f"Shop {shop.name} has no Monero processor with cold wallet configured")
|
||||
logger.error(
|
||||
f"Shop {shop.name} has no Monero processor with cold wallet configured"
|
||||
)
|
||||
sys.exit(1)
|
||||
shops_to_sweep = [shop]
|
||||
elif args.all_shops:
|
||||
|
|
@ -223,16 +225,18 @@ def main():
|
|||
.filter_by(shop_id=shop.id, coin_type="XMR", enabled=True)
|
||||
.first()
|
||||
)
|
||||
|
||||
|
||||
if not xmr_processor:
|
||||
logger.warning(f"Shop {shop.name} has no enabled XMR processor, skipping")
|
||||
continue
|
||||
|
||||
|
||||
print(f"\n=== Sweeping shop: {shop.name} ===")
|
||||
print(f"Account index: {xmr_processor.wallet_label}")
|
||||
print(f"Cold wallet: {xmr_processor.sweep_to_address}")
|
||||
|
||||
account_index = int(xmr_processor.wallet_label) # wallet_label stores the account index
|
||||
account_index = int(
|
||||
xmr_processor.wallet_label
|
||||
) # wallet_label stores the account index
|
||||
|
||||
try:
|
||||
if args.dry_run:
|
||||
|
|
|
|||
|
|
@ -279,9 +279,9 @@ class Cart(RBase, Base):
|
|||
shop_total_in_cents,
|
||||
) in self.shop_totals_in_cents.items():
|
||||
if coupon.shop_uuid_str == shop_uuid:
|
||||
self._discounted_shop_totals_in_cents[
|
||||
shop_uuid
|
||||
] = coupon.compute_discount(shop_total_in_cents)
|
||||
self._discounted_shop_totals_in_cents[shop_uuid] = (
|
||||
coupon.compute_discount(shop_total_in_cents)
|
||||
)
|
||||
return self._discounted_shop_totals_in_cents
|
||||
|
||||
@property
|
||||
|
|
|
|||
|
|
@ -4,7 +4,14 @@ from collections import (
|
|||
)
|
||||
|
||||
from sqlalchemy import (
|
||||
BigInteger, Boolean, Column, Integer, Unicode, UnicodeText, or_, func
|
||||
BigInteger,
|
||||
Boolean,
|
||||
Column,
|
||||
Integer,
|
||||
Unicode,
|
||||
UnicodeText,
|
||||
or_,
|
||||
func,
|
||||
)
|
||||
|
||||
from sqlalchemy.orm import relationship, backref
|
||||
|
|
@ -56,25 +63,25 @@ class Comment(RBase, Base):
|
|||
parent_id = Column(UUIDType, foreign_key("Comment", "id"), default=None)
|
||||
product_id = Column(UUIDType, foreign_key("Product", "id"), default=None)
|
||||
user_id = Column(UUIDType, foreign_key("User", "id"), default=None)
|
||||
|
||||
|
||||
title = Column(Unicode(256), default=None)
|
||||
data = Column(UnicodeText, default=None)
|
||||
data_html = Column(UnicodeText, default=None)
|
||||
|
||||
|
||||
# the depth of this comment in the thread's graph / tree.
|
||||
graph_depth = Column(Integer, nullable=False, default=-1)
|
||||
|
||||
|
||||
created_timestamp = Column(BigInteger, nullable=False)
|
||||
updated_timestamp = Column(BigInteger, nullable=False)
|
||||
disabled_timestamp = Column(BigInteger)
|
||||
disabled = Column(Boolean, default=False)
|
||||
verified = Column(Boolean, default=False)
|
||||
|
||||
|
||||
# a locked thread (root comment) prevents new commenting.
|
||||
locked = Column(Boolean, default=False)
|
||||
# by default comments are approved. unless shop requires approval.
|
||||
approved = Column(Boolean, default=True)
|
||||
|
||||
|
||||
ip_address = Column(Unicode(45), default=None)
|
||||
|
||||
# lazy='joined' performs a left join to reduce queries, it's magic.
|
||||
|
|
@ -103,7 +110,6 @@ class Comment(RBase, Base):
|
|||
overlaps="children,parent",
|
||||
)
|
||||
|
||||
|
||||
def __init__(self):
|
||||
self.id = uuid.uuid1()
|
||||
self.created_timestamp = now_timestamp()
|
||||
|
|
@ -203,54 +209,58 @@ class Comment(RBase, Base):
|
|||
self.disabled_timestamp = None
|
||||
self.stamp_updated_timestamp()
|
||||
|
||||
|
||||
def has_user_purchased_product(self, user_id):
|
||||
"""Check if user has purchased this product (for purchase-required commenting)."""
|
||||
if not self.product:
|
||||
return False
|
||||
|
||||
|
||||
# Check if user has purchased this product
|
||||
from .user_product import UserProduct
|
||||
user_product = self.dbsession.query(UserProduct).filter(
|
||||
UserProduct.user_id == user_id,
|
||||
UserProduct.product_id == self.product_id
|
||||
).first()
|
||||
|
||||
|
||||
user_product = (
|
||||
self.dbsession.query(UserProduct)
|
||||
.filter(
|
||||
UserProduct.user_id == user_id,
|
||||
UserProduct.product_id == self.product_id,
|
||||
)
|
||||
.first()
|
||||
)
|
||||
|
||||
return user_product is not None
|
||||
|
||||
def can_user_comment(self, user, shop):
|
||||
"""Check if user can comment based on shop settings."""
|
||||
if not shop.comments_enabled:
|
||||
return False, "Comments are disabled for this shop"
|
||||
|
||||
|
||||
if self.is_locked:
|
||||
return False, "This comment thread is locked"
|
||||
|
||||
|
||||
if shop.comments_require_purchase and user:
|
||||
if not self.has_user_purchased_product(user.id):
|
||||
return False, "You must purchase this product to leave a comment"
|
||||
|
||||
|
||||
return True, None
|
||||
|
||||
def can_user_comment(self, user, shop):
|
||||
"""Check if user can reply to this comment based on shop settings."""
|
||||
if not shop.comments_enabled:
|
||||
return False, "Comments are disabled for this shop"
|
||||
|
||||
|
||||
if self.is_locked:
|
||||
return False, "This comment thread is locked"
|
||||
|
||||
|
||||
if shop.comments_require_purchase and user:
|
||||
if not self.has_user_purchased_product(user.id):
|
||||
return False, "You must purchase this product to leave a comment"
|
||||
|
||||
|
||||
return True, None
|
||||
|
||||
def can_user_moderate(self, user, shop):
|
||||
"""Check if user can moderate comments (approve, delete, etc)."""
|
||||
if not user:
|
||||
return False
|
||||
|
||||
|
||||
# Shop owners and editors can moderate
|
||||
return shop.is_owner(user) or shop.is_editor(user)
|
||||
|
||||
|
|
@ -265,27 +275,28 @@ def get_comments_for_product(dbsession, product_id, shop=None, user=None):
|
|||
query = dbsession.query(Comment).filter(
|
||||
Comment.product_id == product_id,
|
||||
Comment.parent_id == None,
|
||||
Comment.disabled == False
|
||||
Comment.disabled == False,
|
||||
)
|
||||
|
||||
|
||||
# If shop requires approval, only show approved comments to regular users
|
||||
if shop and shop.comments_require_approval:
|
||||
# Shop owners/editors can see all comments
|
||||
if not (user and (shop.is_owner(user) or shop.is_editor(user))):
|
||||
query = query.filter(Comment.approved == True)
|
||||
|
||||
|
||||
return query.order_by(Comment.created_timestamp.desc()).all()
|
||||
|
||||
|
||||
def get_recent_comments(dbsession, shop_id=None, limit=10):
|
||||
"""Get recent comments, optionally filtered by shop."""
|
||||
query = dbsession.query(Comment).filter(Comment.approved == True)
|
||||
|
||||
|
||||
if shop_id:
|
||||
# Join with Product to filter by shop
|
||||
from .product import Product
|
||||
|
||||
query = query.join(Product).filter(Product.shop_id == shop_id)
|
||||
|
||||
|
||||
return query.order_by(Comment.created_timestamp.desc()).limit(limit).all()
|
||||
|
||||
|
||||
|
|
@ -294,7 +305,7 @@ def get_total_comment_count_for_product(dbsession, product_id, shop=None, user=N
|
|||
query = dbsession.query(Comment).filter(
|
||||
Comment.product_id == product_id,
|
||||
Comment.disabled == False,
|
||||
Comment.approved == True
|
||||
Comment.approved == True,
|
||||
)
|
||||
|
||||
return query.count()
|
||||
|
||||
return query.count()
|
||||
|
|
|
|||
|
|
@ -136,4 +136,3 @@ class CryptoPayment(RBase, Base):
|
|||
return 0
|
||||
# Return the received amount for this specific payment
|
||||
return self.received_amount
|
||||
|
||||
|
|
|
|||
|
|
@ -273,9 +273,12 @@ class Invoice(RBase, Base):
|
|||
try:
|
||||
if hasattr(self, "crypto_payment") and self.crypto_payment:
|
||||
# crypto_payment is a collection, get the first one
|
||||
if hasattr(self.crypto_payment, '__len__') and len(self.crypto_payment) > 0:
|
||||
if (
|
||||
hasattr(self.crypto_payment, "__len__")
|
||||
and len(self.crypto_payment) > 0
|
||||
):
|
||||
return self.crypto_payment[0].coin_type.lower()
|
||||
elif hasattr(self.crypto_payment, 'coin_type'):
|
||||
elif hasattr(self.crypto_payment, "coin_type"):
|
||||
return self.crypto_payment.coin_type.lower()
|
||||
except Exception:
|
||||
# Fall back to stripe if there's any issue accessing crypto_payment
|
||||
|
|
|
|||
|
|
@ -500,32 +500,30 @@ class Product(RBase, Base):
|
|||
return "private"
|
||||
else:
|
||||
return "public-read"
|
||||
|
||||
|
||||
# Product files are always private regardless of visibility
|
||||
# Access is controlled via presigned URLs
|
||||
return "private"
|
||||
|
||||
def update_s3_acls(self, s3_client, bucket_name):
|
||||
"""Update S3 ACLs for all product files based on current visibility."""
|
||||
|
||||
|
||||
# Update ACLs for all file types
|
||||
for file_key in self.file_keys:
|
||||
if file_key in self.extensions:
|
||||
s3_key = getattr(self, f's3_key_{file_key}', None)
|
||||
if s3_key is None and file_key == 'product':
|
||||
s3_key = getattr(self, f"s3_key_{file_key}", None)
|
||||
if s3_key is None and file_key == "product":
|
||||
s3_key = self.s3_key
|
||||
elif s3_key is None and file_key == 'preview':
|
||||
elif s3_key is None and file_key == "preview":
|
||||
s3_key = self.s3_key_preview
|
||||
elif s3_key is None and file_key.startswith('thumbnail'):
|
||||
elif s3_key is None and file_key.startswith("thumbnail"):
|
||||
s3_key = self.s3_key_thumbnail(file_key)
|
||||
|
||||
|
||||
if s3_key:
|
||||
try:
|
||||
acl = self.get_s3_acl_for_file_key(file_key)
|
||||
s3_client.put_object_acl(
|
||||
Bucket=bucket_name,
|
||||
Key=s3_key,
|
||||
ACL=acl
|
||||
Bucket=bucket_name, Key=s3_key, ACL=acl
|
||||
)
|
||||
except Exception as e:
|
||||
# Log error but don't fail the visibility change
|
||||
|
|
@ -535,7 +533,7 @@ class Product(RBase, Base):
|
|||
"""Set product visibility and update S3 ACLs accordingly."""
|
||||
old_visibility = self.visibility
|
||||
self.visibility = new_visibility
|
||||
|
||||
|
||||
# Update S3 ACLs if client provided and visibility changed
|
||||
if s3_client and bucket_name and old_visibility != new_visibility:
|
||||
self.update_s3_acls(s3_client, bucket_name)
|
||||
|
|
@ -543,32 +541,31 @@ class Product(RBase, Base):
|
|||
def has_user_purchased_product(self, user_id):
|
||||
"""Check if user has purchased this product (for purchase-required commenting)."""
|
||||
# Check if user has purchased this product
|
||||
user_product = self.dbsession.query(UserProduct).filter(
|
||||
UserProduct.user_id == user_id,
|
||||
UserProduct.product_id == self.id
|
||||
).first()
|
||||
|
||||
user_product = (
|
||||
self.dbsession.query(UserProduct)
|
||||
.filter(UserProduct.user_id == user_id, UserProduct.product_id == self.id)
|
||||
.first()
|
||||
)
|
||||
|
||||
return user_product is not None
|
||||
|
||||
def can_user_comment(self, user, shop):
|
||||
"""Check if user can comment on this product based on shop settings."""
|
||||
if not shop.comments_enabled:
|
||||
return False, "Comments are disabled for this shop"
|
||||
|
||||
|
||||
if shop.comments_require_purchase and user:
|
||||
if not self.has_user_purchased_product(user.id):
|
||||
return False, "You must purchase this product to leave a comment"
|
||||
|
||||
|
||||
return True, None
|
||||
|
||||
@property
|
||||
def public_comments(self):
|
||||
"""Return only approved, non-disabled comments for public display."""
|
||||
from .comment import Comment
|
||||
return self.comments.filter(
|
||||
Comment.approved == True,
|
||||
Comment.disabled == False
|
||||
)
|
||||
|
||||
return self.comments.filter(Comment.approved == True, Comment.disabled == False)
|
||||
|
||||
@property
|
||||
def public_comment_count(self):
|
||||
|
|
|
|||
|
|
@ -69,7 +69,7 @@ class StripeUserShop(RBase, Base):
|
|||
card = self.get_card_by_id(self.active_card_id)
|
||||
if card:
|
||||
return card
|
||||
|
||||
|
||||
# If no active card or the active card doesn't exist anymore,
|
||||
# automatically set the first available card as active
|
||||
available_cards = self.stripe_cards
|
||||
|
|
@ -78,12 +78,13 @@ class StripeUserShop(RBase, Base):
|
|||
self.active_card_id = available_cards[0].id
|
||||
# Save to database using object_session
|
||||
from sqlalchemy.orm.session import object_session
|
||||
|
||||
session = object_session(self)
|
||||
if session:
|
||||
session.add(self)
|
||||
session.flush()
|
||||
return available_cards[0]
|
||||
|
||||
|
||||
return None
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -94,7 +94,9 @@ def includeme(config):
|
|||
config.add_route("shop_sales", "/s/{shop_id}/sales")
|
||||
|
||||
config.add_route("shop_settings", "/s/{shop_id}/settings")
|
||||
config.add_route("crypto_processor_settings", "/s/{shop_id}/crypto-processor/{coin_type}")
|
||||
config.add_route(
|
||||
"crypto_processor_settings", "/s/{shop_id}/crypto-processor/{coin_type}"
|
||||
)
|
||||
|
||||
config.add_route("shop_users", "/s/{shop_id}/users")
|
||||
config.add_route("shop_user_remove", "/s/{shop_id}/remove-user")
|
||||
|
|
|
|||
|
|
@ -1,4 +1,3 @@
|
|||
|
||||
from logging.config import fileConfig
|
||||
|
||||
from sqlalchemy import engine_from_config
|
||||
|
|
@ -20,6 +19,7 @@ fileConfig(config.config_file_name)
|
|||
# target_metadata = mymodel.Base.metadata
|
||||
|
||||
from make_post_sell.models import Base
|
||||
|
||||
target_metadata = Base.metadata
|
||||
|
||||
# other values from the config, defined by the needs of env.py,
|
||||
|
|
@ -41,9 +41,7 @@ def run_migrations_offline():
|
|||
|
||||
"""
|
||||
url = config.get_main_option("sqlalchemy.url")
|
||||
context.configure(
|
||||
url=url, target_metadata=target_metadata, literal_binds=True
|
||||
)
|
||||
context.configure(url=url, target_metadata=target_metadata, literal_binds=True)
|
||||
|
||||
with context.begin_transaction():
|
||||
context.run_migrations()
|
||||
|
|
@ -63,9 +61,7 @@ def run_migrations_online():
|
|||
)
|
||||
|
||||
with connectable.connect() as connection:
|
||||
context.configure(
|
||||
connection=connection, target_metadata=target_metadata
|
||||
)
|
||||
context.configure(connection=connection, target_metadata=target_metadata)
|
||||
|
||||
with context.begin_transaction():
|
||||
context.run_migrations()
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: e6ac162d096f
|
|||
Create Date: 2022-06-27 12:31:50.885273
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '03292288a132'
|
||||
down_revision = 'e6ac162d096f'
|
||||
revision = "03292288a132"
|
||||
down_revision = "e6ac162d096f"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,11 +21,14 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_user_shop', sa.Column('role_id', sa.Integer(), nullable=False, server_default="0"))
|
||||
op.add_column(
|
||||
"mps_user_shop",
|
||||
sa.Column("role_id", sa.Integer(), nullable=False, server_default="0"),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_user_shop', 'role_id')
|
||||
op.drop_column("mps_user_shop", "role_id")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,20 +5,29 @@ Revises: 201924e6306f
|
|||
Create Date: 2022-07-27 14:50:19.889862
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '1275752bc491'
|
||||
down_revision = '201924e6306f'
|
||||
revision = "1275752bc491"
|
||||
down_revision = "201924e6306f"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('updated_timestamp', sa.BigInteger(), nullable=False, server_default="1657814552131"))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"updated_timestamp",
|
||||
sa.BigInteger(),
|
||||
nullable=False,
|
||||
server_default="1657814552131",
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'updated_timestamp')
|
||||
op.drop_column("mps_shop", "updated_timestamp")
|
||||
|
|
|
|||
|
|
@ -5,24 +5,33 @@ Revises: b0d5604d9255
|
|||
Create Date: 2019-08-11 15:53:30.385027
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '15751f5d7a03'
|
||||
down_revision = 'b0d5604d9255'
|
||||
revision = "15751f5d7a03"
|
||||
down_revision = "b0d5604d9255"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_user', sa.Column('active_cart_total_in_cents', sa.BigInteger(), nullable=False, server_default="0"))
|
||||
op.add_column(
|
||||
"mps_user",
|
||||
sa.Column(
|
||||
"active_cart_total_in_cents",
|
||||
sa.BigInteger(),
|
||||
nullable=False,
|
||||
server_default="0",
|
||||
),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_user', 'active_cart_total_in_cents')
|
||||
op.drop_column("mps_user", "active_cart_total_in_cents")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 81d65d8605c2
|
|||
Create Date: 2025-09-20 21:31:26.257478
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '193438acaa95'
|
||||
down_revision = '81d65d8605c2'
|
||||
revision = "193438acaa95"
|
||||
down_revision = "81d65d8605c2"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,8 +21,16 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# Add crypto quote expiry time column with default of 3600 seconds (60 minutes)
|
||||
op.add_column('mps_shop', sa.Column('crypto_quote_expiry_seconds', sa.BigInteger(), nullable=False, server_default='3600'))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"crypto_quote_expiry_seconds",
|
||||
sa.BigInteger(),
|
||||
nullable=False,
|
||||
server_default="3600",
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'crypto_quote_expiry_seconds')
|
||||
op.drop_column("mps_shop", "crypto_quote_expiry_seconds")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: ddfbd6d96915
|
|||
Create Date: 2024-06-16 14:30:57.649239
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '1b3ecdde9e65'
|
||||
down_revision = 'ddfbd6d96915'
|
||||
revision = "1b3ecdde9e65"
|
||||
down_revision = "ddfbd6d96915"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,17 +21,27 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_cart', sa.Column('handling_option', sa.Unicode(length=64), nullable=True))
|
||||
op.add_column('mps_cart', sa.Column('handling_cost_in_cents', sa.BigInteger(), nullable=True))
|
||||
op.add_column('mps_invoice', sa.Column('handling_option', sa.Unicode(length=64), nullable=True))
|
||||
op.add_column('mps_invoice', sa.Column('handling_cost_in_cents', sa.BigInteger(), nullable=True))
|
||||
op.add_column(
|
||||
"mps_cart", sa.Column("handling_option", sa.Unicode(length=64), nullable=True)
|
||||
)
|
||||
op.add_column(
|
||||
"mps_cart", sa.Column("handling_cost_in_cents", sa.BigInteger(), nullable=True)
|
||||
)
|
||||
op.add_column(
|
||||
"mps_invoice",
|
||||
sa.Column("handling_option", sa.Unicode(length=64), nullable=True),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_invoice",
|
||||
sa.Column("handling_cost_in_cents", sa.BigInteger(), nullable=True),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_invoice', 'handling_cost_in_cents')
|
||||
op.drop_column('mps_invoice', 'handling_option')
|
||||
op.drop_column('mps_cart', 'handling_cost_in_cents')
|
||||
op.drop_column('mps_cart', 'handling_option')
|
||||
op.drop_column("mps_invoice", "handling_cost_in_cents")
|
||||
op.drop_column("mps_invoice", "handling_option")
|
||||
op.drop_column("mps_cart", "handling_cost_in_cents")
|
||||
op.drop_column("mps_cart", "handling_option")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: aad3d454a6f4
|
|||
Create Date: 2022-07-10 13:21:40.740356
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '201924e6306f'
|
||||
down_revision = 'aad3d454a6f4'
|
||||
revision = "201924e6306f"
|
||||
down_revision = "aad3d454a6f4"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,18 +21,18 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_cart', sa.Column('shop_id', UUIDType, nullable=True))
|
||||
op.add_column('mps_cart', sa.Column('active', sa.Boolean(), nullable=True))
|
||||
op.create_index(op.f('ix_mps_cart_id'), 'mps_cart', ['id'], unique=False)
|
||||
#op.create_foreign_key(None, 'mps_cart', 'mps_user', ['user_id'], ['id'])
|
||||
#op.create_foreign_key(None, 'mps_cart', 'mps_shop', ['shop_id'], ['id'])
|
||||
#op.drop_column('mps_user_shop', 'default')
|
||||
op.add_column("mps_cart", sa.Column("shop_id", UUIDType, nullable=True))
|
||||
op.add_column("mps_cart", sa.Column("active", sa.Boolean(), nullable=True))
|
||||
op.create_index(op.f("ix_mps_cart_id"), "mps_cart", ["id"], unique=False)
|
||||
# op.create_foreign_key(None, 'mps_cart', 'mps_user', ['user_id'], ['id'])
|
||||
# op.create_foreign_key(None, 'mps_cart', 'mps_shop', ['shop_id'], ['id'])
|
||||
# op.drop_column('mps_user_shop', 'default')
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_index(op.f('ix_mps_cart_id'), table_name='mps_cart')
|
||||
op.drop_column('mps_cart', 'active')
|
||||
op.drop_column('mps_cart', 'shop_id')
|
||||
op.drop_index(op.f("ix_mps_cart_id"), table_name="mps_cart")
|
||||
op.drop_column("mps_cart", "active")
|
||||
op.drop_column("mps_cart", "shop_id")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 3e1e70bfe89d
|
|||
Create Date: 2020-02-03 00:03:11.599838
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '24662905655f'
|
||||
down_revision = '3e1e70bfe89d'
|
||||
revision = "24662905655f"
|
||||
down_revision = "3e1e70bfe89d"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,8 +20,8 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_user', sa.Column('active_shop_id', UUIDType, nullable=True))
|
||||
op.add_column("mps_user", sa.Column("active_shop_id", UUIDType, nullable=True))
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_user', 'active_shop_id')
|
||||
op.drop_column("mps_user", "active_shop_id")
|
||||
|
|
|
|||
|
|
@ -5,20 +5,24 @@ Revises: eadd0d69e133
|
|||
Create Date: 2019-11-20 11:06:28.092483
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '3e1e70bfe89d'
|
||||
down_revision = 'eadd0d69e133'
|
||||
revision = "3e1e70bfe89d"
|
||||
down_revision = "eadd0d69e133"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('google_analytics_id', sa.Unicode(length=32), nullable=True))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column("google_analytics_id", sa.Unicode(length=32), nullable=True),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'google_analytics_id')
|
||||
op.drop_column("mps_shop", "google_analytics_id")
|
||||
|
|
|
|||
|
|
@ -6,13 +6,14 @@ Revises: af28cc35ed6f
|
|||
Create Date: 2021-10-27 09:00:32.238571
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '4d9da43b0e86'
|
||||
down_revision = 'af28cc35ed6f'
|
||||
revision = "4d9da43b0e86"
|
||||
down_revision = "af28cc35ed6f"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,8 +21,11 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_product', sa.Column('visibility', sa.Integer(), nullable=False, server_default="1"))
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column("visibility", sa.Integer(), nullable=False, server_default="1"),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_product', 'visibility')
|
||||
op.drop_column("mps_product", "visibility")
|
||||
|
|
|
|||
|
|
@ -5,24 +5,29 @@ Revises: f882f2255cd1
|
|||
Create Date: 2019-10-29 11:59:01.050032
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '5c40dfb56179'
|
||||
down_revision = 'f882f2255cd1'
|
||||
revision = "5c40dfb56179"
|
||||
down_revision = "f882f2255cd1"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('ribbon_color_1', sa.Unicode(length=32), nullable=True))
|
||||
op.add_column('mps_shop', sa.Column('ribbon_color_2', sa.Unicode(length=32), nullable=True))
|
||||
op.add_column('mps_shop', sa.Column('ribbon_text', sa.UnicodeText(), nullable=True))
|
||||
op.add_column(
|
||||
"mps_shop", sa.Column("ribbon_color_1", sa.Unicode(length=32), nullable=True)
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop", sa.Column("ribbon_color_2", sa.Unicode(length=32), nullable=True)
|
||||
)
|
||||
op.add_column("mps_shop", sa.Column("ribbon_text", sa.UnicodeText(), nullable=True))
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'ribbon_text')
|
||||
op.drop_column('mps_shop', 'ribbon_color_2')
|
||||
op.drop_column('mps_shop', 'ribbon_color_1')
|
||||
op.drop_column("mps_shop", "ribbon_text")
|
||||
op.drop_column("mps_shop", "ribbon_color_2")
|
||||
op.drop_column("mps_shop", "ribbon_color_1")
|
||||
|
|
|
|||
|
|
@ -5,24 +5,30 @@ Revises: 15751f5d7a03
|
|||
Create Date: 2019-08-13 08:52:18.073705
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '6da97f2f913f'
|
||||
down_revision = '15751f5d7a03'
|
||||
revision = "6da97f2f913f"
|
||||
down_revision = "15751f5d7a03"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_cart', sa.Column('updated_timestamp', sa.BigInteger(), nullable=False, server_default="0"))
|
||||
op.add_column(
|
||||
"mps_cart",
|
||||
sa.Column(
|
||||
"updated_timestamp", sa.BigInteger(), nullable=False, server_default="0"
|
||||
),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_cart', 'updated_timestamp')
|
||||
op.drop_column("mps_cart", "updated_timestamp")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: d38d649cb682
|
|||
Create Date: 2022-09-13 14:57:57.100700
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '7217f39a20a8'
|
||||
down_revision = 'd38d649cb682'
|
||||
revision = "7217f39a20a8"
|
||||
down_revision = "d38d649cb682"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,10 +20,20 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_product', sa.Column('json_file_bytes', sa.UnicodeText(), nullable=True, server_default="{}"))
|
||||
op.add_column('mps_product', sa.Column('total_file_bytes', sa.BigInteger(), nullable=False, server_default="0"))
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column(
|
||||
"json_file_bytes", sa.UnicodeText(), nullable=True, server_default="{}"
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column(
|
||||
"total_file_bytes", sa.BigInteger(), nullable=False, server_default="0"
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_product', 'total_file_bytes')
|
||||
op.drop_column('mps_product', 'json_file_bytes')
|
||||
op.drop_column("mps_product", "total_file_bytes")
|
||||
op.drop_column("mps_product", "json_file_bytes")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 1b3ecdde9e65, fd9f7e2f2b78
|
|||
Create Date: 2025-06-24 08:09:33.656088
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '81d65d8605c2'
|
||||
down_revision = ('1b3ecdde9e65', 'fd9f7e2f2b78')
|
||||
revision = "81d65d8605c2"
|
||||
down_revision = ("1b3ecdde9e65", "fd9f7e2f2b78")
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -23,30 +24,51 @@ def upgrade():
|
|||
import sqlalchemy as sa
|
||||
from alembic import op
|
||||
from sqlalchemy import text
|
||||
|
||||
|
||||
# Check if columns exist before adding them
|
||||
conn = op.get_bind()
|
||||
|
||||
|
||||
# Check if comments_enabled exists
|
||||
try:
|
||||
conn.execute(text("SELECT comments_enabled FROM mps_shop LIMIT 1"))
|
||||
except:
|
||||
op.add_column('mps_shop', sa.Column('comments_enabled', sa.Boolean(), nullable=True, server_default="1"))
|
||||
|
||||
# Check if comments_require_purchase exists
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"comments_enabled", sa.Boolean(), nullable=True, server_default="1"
|
||||
),
|
||||
)
|
||||
|
||||
# Check if comments_require_purchase exists
|
||||
try:
|
||||
conn.execute(text("SELECT comments_require_purchase FROM mps_shop LIMIT 1"))
|
||||
except:
|
||||
op.add_column('mps_shop', sa.Column('comments_require_purchase', sa.Boolean(), nullable=True, server_default="0"))
|
||||
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"comments_require_purchase",
|
||||
sa.Boolean(),
|
||||
nullable=True,
|
||||
server_default="0",
|
||||
),
|
||||
)
|
||||
|
||||
# Check if comments_require_approval exists
|
||||
try:
|
||||
conn.execute(text("SELECT comments_require_approval FROM mps_shop LIMIT 1"))
|
||||
except:
|
||||
op.add_column('mps_shop', sa.Column('comments_require_approval', sa.Boolean(), nullable=True, server_default="0"))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"comments_require_approval",
|
||||
sa.Boolean(),
|
||||
nullable=True,
|
||||
server_default="0",
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'comments_require_approval')
|
||||
op.drop_column('mps_shop', 'comments_require_purchase')
|
||||
op.drop_column('mps_shop', 'comments_enabled')
|
||||
op.drop_column("mps_shop", "comments_require_approval")
|
||||
op.drop_column("mps_shop", "comments_require_purchase")
|
||||
op.drop_column("mps_shop", "comments_enabled")
|
||||
|
|
|
|||
|
|
@ -5,26 +5,47 @@ Revises: 24662905655f
|
|||
Create Date: 2020-03-21 18:34:12.244626
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '96f851cbab01'
|
||||
down_revision = '24662905655f'
|
||||
revision = "96f851cbab01"
|
||||
down_revision = "24662905655f"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('privacy_policy_html', sa.UnicodeText(), nullable=True, server_default=""))
|
||||
op.add_column('mps_shop', sa.Column('privacy_policy_raw', sa.UnicodeText(), nullable=True, server_default=""))
|
||||
op.add_column('mps_shop', sa.Column('terms_of_service_html', sa.UnicodeText(), nullable=True, server_default=""))
|
||||
op.add_column('mps_shop', sa.Column('terms_of_service_raw', sa.UnicodeText(), nullable=True, server_default=""))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"privacy_policy_html", sa.UnicodeText(), nullable=True, server_default=""
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"privacy_policy_raw", sa.UnicodeText(), nullable=True, server_default=""
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"terms_of_service_html", sa.UnicodeText(), nullable=True, server_default=""
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"terms_of_service_raw", sa.UnicodeText(), nullable=True, server_default=""
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'terms_of_service_raw')
|
||||
op.drop_column('mps_shop', 'terms_of_service_html')
|
||||
op.drop_column('mps_shop', 'privacy_policy_raw')
|
||||
op.drop_column('mps_shop', 'privacy_policy_html')
|
||||
op.drop_column("mps_shop", "terms_of_service_raw")
|
||||
op.drop_column("mps_shop", "terms_of_service_html")
|
||||
op.drop_column("mps_shop", "privacy_policy_raw")
|
||||
op.drop_column("mps_shop", "privacy_policy_html")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 03292288a132
|
|||
Create Date: 2022-06-30 16:48:22.471896
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'aad3d454a6f4'
|
||||
down_revision = '03292288a132'
|
||||
revision = "aad3d454a6f4"
|
||||
down_revision = "03292288a132"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,11 +21,14 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_shop', sa.Column('logo_banner', sa.Boolean(), nullable=True, server_default="1"))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column("logo_banner", sa.Boolean(), nullable=True, server_default="1"),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_shop', 'logo_banner')
|
||||
op.drop_column("mps_shop", "logo_banner")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,19 +5,25 @@ Revises: fd9f7e2f2b78
|
|||
Create Date: 2019-08-10 11:20:43.838087
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'ab7338eaedf1'
|
||||
down_revision = 'fd9f7e2f2b78'
|
||||
revision = "ab7338eaedf1"
|
||||
down_revision = "fd9f7e2f2b78"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_product', sa.Column('price_in_cents', sa.BigInteger(), nullable=False, server_default="3.50"))
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column(
|
||||
"price_in_cents", sa.BigInteger(), nullable=False, server_default="3.50"
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: c4d5566ec87d
|
|||
Create Date: 2021-04-15 09:30:53.107239
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'af28cc35ed6f'
|
||||
down_revision = 'c4d5566ec87d'
|
||||
revision = "af28cc35ed6f"
|
||||
down_revision = "c4d5566ec87d"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -22,13 +23,24 @@ from make_post_sell.models.product import DEFAULT_BUNDLE_METADATA
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_product', sa.Column('is_bundle', sa.Boolean(), nullable=False, server_default="0"))
|
||||
op.add_column('mps_product', sa.Column('json_bundle_metadata', sa.UnicodeText(), nullable=False, server_default=DEFAULT_BUNDLE_METADATA))
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column("is_bundle", sa.Boolean(), nullable=False, server_default="0"),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column(
|
||||
"json_bundle_metadata",
|
||||
sa.UnicodeText(),
|
||||
nullable=False,
|
||||
server_default=DEFAULT_BUNDLE_METADATA,
|
||||
),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_product', 'json_bundle_metadata')
|
||||
op.drop_column('mps_product', 'is_bundle')
|
||||
op.drop_column("mps_product", "json_bundle_metadata")
|
||||
op.drop_column("mps_product", "is_bundle")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,24 +5,30 @@ Revises: ab7338eaedf1
|
|||
Create Date: 2019-08-10 20:15:45.595633
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'b0d5604d9255'
|
||||
down_revision = 'ab7338eaedf1'
|
||||
revision = "b0d5604d9255"
|
||||
down_revision = "ab7338eaedf1"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_user', sa.Column('active_cart_count', sa.Integer(), server_default="0", nullable=False))
|
||||
op.add_column(
|
||||
"mps_user",
|
||||
sa.Column(
|
||||
"active_cart_count", sa.Integer(), server_default="0", nullable=False
|
||||
),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_user', 'active_cart_count')
|
||||
op.drop_column("mps_user", "active_cart_count")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 1275752bc491
|
|||
Create Date: 2022-08-03 11:53:34.191328
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'b8be6cd51cbd'
|
||||
down_revision = '1275752bc491'
|
||||
revision = "b8be6cd51cbd"
|
||||
down_revision = "1275752bc491"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,9 +20,11 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_stripe_user_shop', sa.Column('active_card_id', sa.Unicode(length=64), nullable=True))
|
||||
op.add_column(
|
||||
"mps_stripe_user_shop",
|
||||
sa.Column("active_card_id", sa.Unicode(length=64), nullable=True),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_stripe_user_shop', 'active_card_id')
|
||||
|
||||
op.drop_column("mps_stripe_user_shop", "active_card_id")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 4d9da43b0e86
|
|||
Create Date: 2021-12-02 17:32:08.498999
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'bfc4195a7f56'
|
||||
down_revision = '4d9da43b0e86'
|
||||
revision = "bfc4195a7f56"
|
||||
down_revision = "4d9da43b0e86"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,8 +20,11 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_product', sa.Column('is_sellable', sa.Boolean(), nullable=False, server_default="1"))
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column("is_sellable", sa.Boolean(), nullable=False, server_default="1"),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_product', 'is_sellable')
|
||||
op.drop_column("mps_product", "is_sellable")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: cdad5c220c39
|
|||
Create Date: 2022-01-31 15:45:34.314442
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'c263b4fba9e7'
|
||||
down_revision = 'cdad5c220c39'
|
||||
revision = "c263b4fba9e7"
|
||||
down_revision = "cdad5c220c39"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,12 +20,21 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('maint_mode', sa.Boolean(), nullable=True, server_default="0"))
|
||||
op.add_column('mps_shop', sa.Column('favicon', sa.Boolean(), nullable=True, server_default="0"))
|
||||
op.add_column('mps_user', sa.Column('theme_id', sa.BigInteger(), nullable=False, server_default="1"))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column("maint_mode", sa.Boolean(), nullable=True, server_default="0"),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column("favicon", sa.Boolean(), nullable=True, server_default="0"),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_user",
|
||||
sa.Column("theme_id", sa.BigInteger(), nullable=False, server_default="1"),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'maint_mode')
|
||||
op.drop_column('mps_shop', 'favicon')
|
||||
op.drop_column('mps_user', 'theme_id')
|
||||
op.drop_column("mps_shop", "maint_mode")
|
||||
op.drop_column("mps_shop", "favicon")
|
||||
op.drop_column("mps_user", "theme_id")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: e12bbe39d87e
|
|||
Create Date: 2021-01-16 11:18:10.302974
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'c4d5566ec87d'
|
||||
down_revision = 'e12bbe39d87e'
|
||||
revision = "c4d5566ec87d"
|
||||
down_revision = "e12bbe39d87e"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,24 +20,47 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.create_table('mps_coupon_redemption',
|
||||
sa.Column('id', UUIDType, nullable=False),
|
||||
sa.Column('coupon_id', UUIDType, nullable=False),
|
||||
sa.Column('invoice_id', UUIDType, nullable=False),
|
||||
sa.Column('shop_id', UUIDType, nullable=False),
|
||||
sa.Column('user_id', UUIDType, nullable=False),
|
||||
sa.Column('created_timestamp', sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(['coupon_id'], ['mps_coupon.id'], ),
|
||||
sa.ForeignKeyConstraint(['invoice_id'], ['mps_invoice.id'], ),
|
||||
sa.ForeignKeyConstraint(['shop_id'], ['mps_shop.id'], ),
|
||||
sa.ForeignKeyConstraint(['user_id'], ['mps_user.id'], ),
|
||||
sa.PrimaryKeyConstraint('id')
|
||||
op.create_table(
|
||||
"mps_coupon_redemption",
|
||||
sa.Column("id", UUIDType, nullable=False),
|
||||
sa.Column("coupon_id", UUIDType, nullable=False),
|
||||
sa.Column("invoice_id", UUIDType, nullable=False),
|
||||
sa.Column("shop_id", UUIDType, nullable=False),
|
||||
sa.Column("user_id", UUIDType, nullable=False),
|
||||
sa.Column("created_timestamp", sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(
|
||||
["coupon_id"],
|
||||
["mps_coupon.id"],
|
||||
),
|
||||
sa.ForeignKeyConstraint(
|
||||
["invoice_id"],
|
||||
["mps_invoice.id"],
|
||||
),
|
||||
sa.ForeignKeyConstraint(
|
||||
["shop_id"],
|
||||
["mps_shop.id"],
|
||||
),
|
||||
sa.ForeignKeyConstraint(
|
||||
["user_id"],
|
||||
["mps_user.id"],
|
||||
),
|
||||
sa.PrimaryKeyConstraint("id"),
|
||||
)
|
||||
op.create_index(
|
||||
op.f("ix_mps_coupon_redemption_id"),
|
||||
"mps_coupon_redemption",
|
||||
["id"],
|
||||
unique=True,
|
||||
)
|
||||
op.add_column(
|
||||
"mps_coupon",
|
||||
sa.Column("stackable", sa.Boolean(), nullable=False, server_default="0"),
|
||||
)
|
||||
op.create_index(op.f('ix_mps_coupon_redemption_id'), 'mps_coupon_redemption', ['id'], unique=True)
|
||||
op.add_column(u'mps_coupon', sa.Column('stackable', sa.Boolean(), nullable=False, server_default="0"))
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column(u'mps_coupon', 'stackable')
|
||||
op.drop_index(op.f('ix_mps_coupon_redemption_id'), table_name='mps_coupon_redemption')
|
||||
op.drop_table('mps_coupon_redemption')
|
||||
op.drop_column("mps_coupon", "stackable")
|
||||
op.drop_index(
|
||||
op.f("ix_mps_coupon_redemption_id"), table_name="mps_coupon_redemption"
|
||||
)
|
||||
op.drop_table("mps_coupon_redemption")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 7217f39a20a8
|
|||
Create Date: 2024-06-08 09:40:24.200194
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'cc6211ec360e'
|
||||
down_revision = '7217f39a20a8'
|
||||
revision = "cc6211ec360e"
|
||||
down_revision = "7217f39a20a8"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,42 +21,60 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.create_table('mps_shop_location',
|
||||
sa.Column('id', UUIDType, nullable=False),
|
||||
sa.Column('shop_id', UUIDType, nullable=False),
|
||||
sa.Column('name', sa.Unicode(length=64), nullable=False),
|
||||
sa.Column('address', sa.Unicode(length=256), nullable=False),
|
||||
sa.Column('city', sa.Unicode(length=64), nullable=False),
|
||||
sa.Column('state', sa.Unicode(length=64), nullable=False),
|
||||
sa.Column('country', sa.Unicode(length=64), nullable=False),
|
||||
sa.Column('postal_code', sa.Unicode(length=16), nullable=False),
|
||||
sa.Column('created_timestamp', sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(['shop_id'], ['mps_shop.id'], ),
|
||||
sa.PrimaryKeyConstraint('id')
|
||||
op.create_table(
|
||||
"mps_shop_location",
|
||||
sa.Column("id", UUIDType, nullable=False),
|
||||
sa.Column("shop_id", UUIDType, nullable=False),
|
||||
sa.Column("name", sa.Unicode(length=64), nullable=False),
|
||||
sa.Column("address", sa.Unicode(length=256), nullable=False),
|
||||
sa.Column("city", sa.Unicode(length=64), nullable=False),
|
||||
sa.Column("state", sa.Unicode(length=64), nullable=False),
|
||||
sa.Column("country", sa.Unicode(length=64), nullable=False),
|
||||
sa.Column("postal_code", sa.Unicode(length=16), nullable=False),
|
||||
sa.Column("created_timestamp", sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(
|
||||
["shop_id"],
|
||||
["mps_shop.id"],
|
||||
),
|
||||
sa.PrimaryKeyConstraint("id"),
|
||||
)
|
||||
op.create_index(op.f('ix_mps_shop_location_id'), 'mps_shop_location', ['id'], unique=False)
|
||||
op.create_table('mps_inventory',
|
||||
sa.Column('id', UUIDType, nullable=False),
|
||||
sa.Column('shop_location_id', UUIDType, nullable=False),
|
||||
sa.Column('product_id', UUIDType, nullable=False),
|
||||
sa.Column('quantity', sa.Integer(), nullable=False),
|
||||
sa.Column('created_timestamp', sa.BigInteger(), nullable=False),
|
||||
sa.Column('updated_timestamp', sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(['product_id'], ['mps_product.id'], ),
|
||||
sa.ForeignKeyConstraint(['shop_location_id'], ['mps_shop_location.id'], ),
|
||||
sa.PrimaryKeyConstraint('id')
|
||||
op.create_index(
|
||||
op.f("ix_mps_shop_location_id"), "mps_shop_location", ["id"], unique=False
|
||||
)
|
||||
op.create_index(op.f('ix_mps_inventory_id'), 'mps_inventory', ['id'], unique=False)
|
||||
op.create_table(
|
||||
"mps_inventory",
|
||||
sa.Column("id", UUIDType, nullable=False),
|
||||
sa.Column("shop_location_id", UUIDType, nullable=False),
|
||||
sa.Column("product_id", UUIDType, nullable=False),
|
||||
sa.Column("quantity", sa.Integer(), nullable=False),
|
||||
sa.Column("created_timestamp", sa.BigInteger(), nullable=False),
|
||||
sa.Column("updated_timestamp", sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(
|
||||
["product_id"],
|
||||
["mps_product.id"],
|
||||
),
|
||||
sa.ForeignKeyConstraint(
|
||||
["shop_location_id"],
|
||||
["mps_shop_location.id"],
|
||||
),
|
||||
sa.PrimaryKeyConstraint("id"),
|
||||
)
|
||||
op.create_index(op.f("ix_mps_inventory_id"), "mps_inventory", ["id"], unique=False)
|
||||
|
||||
op.add_column('mps_product', sa.Column('is_physical', sa.Boolean(), nullable=False, server_default=sa.false()))
|
||||
op.add_column(
|
||||
"mps_product",
|
||||
sa.Column(
|
||||
"is_physical", sa.Boolean(), nullable=False, server_default=sa.false()
|
||||
),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_product', 'is_physical')
|
||||
op.drop_index(op.f('ix_mps_inventory_id'), table_name='mps_inventory')
|
||||
op.drop_table('mps_inventory')
|
||||
op.drop_index(op.f('ix_mps_shop_location_id'), table_name='mps_shop_location')
|
||||
op.drop_table('mps_shop_location')
|
||||
op.drop_column("mps_product", "is_physical")
|
||||
op.drop_index(op.f("ix_mps_inventory_id"), table_name="mps_inventory")
|
||||
op.drop_table("mps_inventory")
|
||||
op.drop_index(op.f("ix_mps_shop_location_id"), table_name="mps_shop_location")
|
||||
op.drop_table("mps_shop_location")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,20 +5,29 @@ Revises: bfc4195a7f56
|
|||
Create Date: 2022-01-07 19:57:52.202252
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'cdad5c220c39'
|
||||
down_revision = 'bfc4195a7f56'
|
||||
revision = "cdad5c220c39"
|
||||
down_revision = "bfc4195a7f56"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('plausible_domain_name', sa.Unicode(length=256), nullable=True, server_default=""))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column(
|
||||
"plausible_domain_name",
|
||||
sa.Unicode(length=256),
|
||||
nullable=True,
|
||||
server_default="",
|
||||
),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'plausible_domain_name')
|
||||
op.drop_column("mps_shop", "plausible_domain_name")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: b8be6cd51cbd
|
|||
Create Date: 2022-09-03 12:46:49.118477
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'd38d649cb682'
|
||||
down_revision = 'b8be6cd51cbd'
|
||||
revision = "d38d649cb682"
|
||||
down_revision = "b8be6cd51cbd"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,12 +21,14 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_invoice', sa.Column('delivery_address', sa.UnicodeText(), nullable=True))
|
||||
op.add_column('mps_user', sa.Column('active_address_id', UUIDType, nullable=True))
|
||||
op.add_column(
|
||||
"mps_invoice", sa.Column("delivery_address", sa.UnicodeText(), nullable=True)
|
||||
)
|
||||
op.add_column("mps_user", sa.Column("active_address_id", UUIDType, nullable=True))
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_user', 'active_address_id')
|
||||
op.drop_column('mps_invoice', 'delivery_address')
|
||||
op.drop_column("mps_user", "active_address_id")
|
||||
op.drop_column("mps_invoice", "delivery_address")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: cc6211ec360e
|
|||
Create Date: 2024-06-08 11:38:38.812584
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'ddfbd6d96915'
|
||||
down_revision = 'cc6211ec360e'
|
||||
revision = "ddfbd6d96915"
|
||||
down_revision = "cc6211ec360e"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,27 +21,67 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_shop_location', sa.Column('local_pickup', sa.Boolean(), nullable=False, server_default=sa.false()))
|
||||
op.add_column('mps_shop_location', sa.Column('local_delivery', sa.Boolean(), nullable=False, server_default=sa.false()))
|
||||
op.add_column('mps_shop_location', sa.Column('local_shipping', sa.Boolean(), nullable=False, server_default=sa.false()))
|
||||
op.add_column('mps_shop_location', sa.Column('international_shipping', sa.Boolean(), nullable=False, server_default=sa.false()))
|
||||
op.add_column('mps_shop_location', sa.Column('local_delivery_rate_in_cents', sa.BigInteger(), nullable=True))
|
||||
op.add_column('mps_shop_location', sa.Column('local_shipping_rate_in_cents', sa.BigInteger(), nullable=True))
|
||||
op.add_column('mps_shop_location', sa.Column('international_shipping_rate_in_cents', sa.BigInteger(), nullable=True))
|
||||
op.add_column('mps_shop_location', sa.Column('days_open', sa.Unicode(length=64), nullable=True))
|
||||
op.add_column('mps_shop_location', sa.Column('hours_open', sa.Unicode(length=64), nullable=True))
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column(
|
||||
"local_pickup", sa.Boolean(), nullable=False, server_default=sa.false()
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column(
|
||||
"local_delivery", sa.Boolean(), nullable=False, server_default=sa.false()
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column(
|
||||
"local_shipping", sa.Boolean(), nullable=False, server_default=sa.false()
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column(
|
||||
"international_shipping",
|
||||
sa.Boolean(),
|
||||
nullable=False,
|
||||
server_default=sa.false(),
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column("local_delivery_rate_in_cents", sa.BigInteger(), nullable=True),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column("local_shipping_rate_in_cents", sa.BigInteger(), nullable=True),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column(
|
||||
"international_shipping_rate_in_cents", sa.BigInteger(), nullable=True
|
||||
),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column("days_open", sa.Unicode(length=64), nullable=True),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop_location",
|
||||
sa.Column("hours_open", sa.Unicode(length=64), nullable=True),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_shop_location', 'hours_open')
|
||||
op.drop_column('mps_shop_location', 'days_open')
|
||||
op.drop_column('mps_shop_location', 'international_shipping_rate_in_cents')
|
||||
op.drop_column('mps_shop_location', 'local_shipping_rate_in_cents')
|
||||
op.drop_column('mps_shop_location', 'local_delivery_rate_in_cents')
|
||||
op.drop_column('mps_shop_location', 'international_shipping')
|
||||
op.drop_column('mps_shop_location', 'local_shipping')
|
||||
op.drop_column('mps_shop_location', 'local_delivery')
|
||||
op.drop_column('mps_shop_location', 'local_pickup')
|
||||
op.drop_column("mps_shop_location", "hours_open")
|
||||
op.drop_column("mps_shop_location", "days_open")
|
||||
op.drop_column("mps_shop_location", "international_shipping_rate_in_cents")
|
||||
op.drop_column("mps_shop_location", "local_shipping_rate_in_cents")
|
||||
op.drop_column("mps_shop_location", "local_delivery_rate_in_cents")
|
||||
op.drop_column("mps_shop_location", "international_shipping")
|
||||
op.drop_column("mps_shop_location", "local_shipping")
|
||||
op.drop_column("mps_shop_location", "local_delivery")
|
||||
op.drop_column("mps_shop_location", "local_pickup")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: f3aa57777025
|
|||
Create Date: 2020-08-23 12:48:47.259833
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'e12bbe39d87e'
|
||||
down_revision = 'f3aa57777025'
|
||||
revision = "e12bbe39d87e"
|
||||
down_revision = "f3aa57777025"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,21 +21,30 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.create_table('mps_cart_coupon',
|
||||
sa.Column('id', UUIDType, nullable=False),
|
||||
sa.Column('cart_id', UUIDType, nullable=False),
|
||||
sa.Column('coupon_id', UUIDType, nullable=False),
|
||||
sa.Column('created_timestamp', sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(['cart_id'], ['mps_cart.id'], ),
|
||||
sa.ForeignKeyConstraint(['coupon_id'], ['mps_coupon.id'], ),
|
||||
sa.PrimaryKeyConstraint('id')
|
||||
op.create_table(
|
||||
"mps_cart_coupon",
|
||||
sa.Column("id", UUIDType, nullable=False),
|
||||
sa.Column("cart_id", UUIDType, nullable=False),
|
||||
sa.Column("coupon_id", UUIDType, nullable=False),
|
||||
sa.Column("created_timestamp", sa.BigInteger(), nullable=False),
|
||||
sa.ForeignKeyConstraint(
|
||||
["cart_id"],
|
||||
["mps_cart.id"],
|
||||
),
|
||||
sa.ForeignKeyConstraint(
|
||||
["coupon_id"],
|
||||
["mps_coupon.id"],
|
||||
),
|
||||
sa.PrimaryKeyConstraint("id"),
|
||||
)
|
||||
op.create_index(
|
||||
op.f("ix_mps_cart_coupon_id"), "mps_cart_coupon", ["id"], unique=False
|
||||
)
|
||||
op.create_index(op.f('ix_mps_cart_coupon_id'), 'mps_cart_coupon', ['id'], unique=False)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_index(op.f('ix_mps_cart_coupon_id'), table_name='mps_cart_coupon')
|
||||
op.drop_table('mps_cart_coupon')
|
||||
op.drop_index(op.f("ix_mps_cart_coupon_id"), table_name="mps_cart_coupon")
|
||||
op.drop_table("mps_cart_coupon")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: c263b4fba9e7
|
|||
Create Date: 2022-06-09 20:52:58.235423
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'e6ac162d096f'
|
||||
down_revision = 'c263b4fba9e7'
|
||||
revision = "e6ac162d096f"
|
||||
down_revision = "c263b4fba9e7"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -19,8 +20,11 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_user', sa.Column('password_attempts', sa.Integer(), nullable=True, server_default="0"))
|
||||
op.add_column(
|
||||
"mps_user",
|
||||
sa.Column("password_attempts", sa.Integer(), nullable=True, server_default="0"),
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_user', 'password_attempts')
|
||||
op.drop_column("mps_user", "password_attempts")
|
||||
|
|
|
|||
|
|
@ -5,20 +5,23 @@ Revises: 5c40dfb56179
|
|||
Create Date: 2019-10-29 12:14:10.391983
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'eadd0d69e133'
|
||||
down_revision = '5c40dfb56179'
|
||||
revision = "eadd0d69e133"
|
||||
down_revision = "5c40dfb56179"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
op.add_column('mps_shop', sa.Column('ribbon_text_color', sa.Unicode(length=32), nullable=True))
|
||||
op.add_column(
|
||||
"mps_shop", sa.Column("ribbon_text_color", sa.Unicode(length=32), nullable=True)
|
||||
)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_column('mps_shop', 'ribbon_text_color')
|
||||
op.drop_column("mps_shop", "ribbon_text_color")
|
||||
|
|
|
|||
|
|
@ -5,13 +5,14 @@ Revises: 96f851cbab01
|
|||
Create Date: 2020-07-27 10:11:58.760190
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'f3aa57777025'
|
||||
down_revision = '96f851cbab01'
|
||||
revision = "f3aa57777025"
|
||||
down_revision = "96f851cbab01"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
|
@ -20,26 +21,34 @@ from make_post_sell.models.meta import UUIDType
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.create_table('mps_coupon',
|
||||
sa.Column('id', UUIDType, nullable=False),
|
||||
sa.Column('shop_id', UUIDType, nullable=False),
|
||||
sa.Column('code', sa.Unicode(length=256), nullable=False),
|
||||
sa.Column('description', sa.Unicode(length=256), nullable=False),
|
||||
sa.Column('action_type', sa.Enum('percent-off', 'dollar-off', name='action_type'), nullable=False),
|
||||
sa.Column('action_value', sa.BigInteger(), nullable=False),
|
||||
sa.Column('redemptions', sa.BigInteger(), nullable=False),
|
||||
sa.Column('max_redemptions', sa.BigInteger(), nullable=True),
|
||||
sa.Column('max_redemptions_per_user', sa.BigInteger(), nullable=True),
|
||||
sa.Column('cart_qualifier', sa.BigInteger(), nullable=True),
|
||||
sa.Column('created_timestamp', sa.BigInteger(), nullable=False),
|
||||
sa.Column('expired_timestamp', sa.BigInteger(), nullable=True),
|
||||
sa.Column('disabled', sa.Boolean(), nullable=True),
|
||||
sa.ForeignKeyConstraint(['shop_id'], ['mps_shop.id'], ),
|
||||
sa.PrimaryKeyConstraint('id')
|
||||
op.create_table(
|
||||
"mps_coupon",
|
||||
sa.Column("id", UUIDType, nullable=False),
|
||||
sa.Column("shop_id", UUIDType, nullable=False),
|
||||
sa.Column("code", sa.Unicode(length=256), nullable=False),
|
||||
sa.Column("description", sa.Unicode(length=256), nullable=False),
|
||||
sa.Column(
|
||||
"action_type",
|
||||
sa.Enum("percent-off", "dollar-off", name="action_type"),
|
||||
nullable=False,
|
||||
),
|
||||
sa.Column("action_value", sa.BigInteger(), nullable=False),
|
||||
sa.Column("redemptions", sa.BigInteger(), nullable=False),
|
||||
sa.Column("max_redemptions", sa.BigInteger(), nullable=True),
|
||||
sa.Column("max_redemptions_per_user", sa.BigInteger(), nullable=True),
|
||||
sa.Column("cart_qualifier", sa.BigInteger(), nullable=True),
|
||||
sa.Column("created_timestamp", sa.BigInteger(), nullable=False),
|
||||
sa.Column("expired_timestamp", sa.BigInteger(), nullable=True),
|
||||
sa.Column("disabled", sa.Boolean(), nullable=True),
|
||||
sa.ForeignKeyConstraint(
|
||||
["shop_id"],
|
||||
["mps_shop.id"],
|
||||
),
|
||||
sa.PrimaryKeyConstraint("id"),
|
||||
)
|
||||
op.create_index(op.f('ix_mps_coupon_id'), 'mps_coupon', ['id'], unique=False)
|
||||
op.create_index(op.f("ix_mps_coupon_id"), "mps_coupon", ["id"], unique=False)
|
||||
|
||||
|
||||
def downgrade():
|
||||
op.drop_index(op.f('ix_mps_coupon_id'), table_name='mps_coupon')
|
||||
op.drop_table('mps_coupon')
|
||||
op.drop_index(op.f("ix_mps_coupon_id"), table_name="mps_coupon")
|
||||
op.drop_table("mps_coupon")
|
||||
|
|
|
|||
|
|
@ -5,21 +5,28 @@ Revises: 6da97f2f913f
|
|||
Create Date: 2019-08-25 13:46:12.004425
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'f882f2255cd1'
|
||||
down_revision = '6da97f2f913f'
|
||||
revision = "f882f2255cd1"
|
||||
down_revision = "6da97f2f913f"
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
||||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_shop', sa.Column('stripe_public_api_key', sa.Unicode(length=32), nullable=True))
|
||||
op.add_column('mps_shop', sa.Column('stripe_secret_api_key', sa.Unicode(length=32), nullable=True))
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column("stripe_public_api_key", sa.Unicode(length=32), nullable=True),
|
||||
)
|
||||
op.add_column(
|
||||
"mps_shop",
|
||||
sa.Column("stripe_secret_api_key", sa.Unicode(length=32), nullable=True),
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -5,12 +5,13 @@ Revises:
|
|||
Create Date: 2019-08-05 21:46:20.974126
|
||||
|
||||
"""
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = 'fd9f7e2f2b78'
|
||||
revision = "fd9f7e2f2b78"
|
||||
down_revision = None
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
|
|
@ -18,11 +19,13 @@ depends_on = None
|
|||
|
||||
def upgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.add_column('mps_user', sa.Column('full_name', sa.Unicode(length=64), nullable=True))
|
||||
op.add_column(
|
||||
"mps_user", sa.Column("full_name", sa.Unicode(length=64), nullable=True)
|
||||
)
|
||||
# ### end Alembic commands ###
|
||||
|
||||
|
||||
def downgrade():
|
||||
# ### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_column('mps_user', 'full_name')
|
||||
op.drop_column("mps_user", "full_name")
|
||||
# ### end Alembic commands ###
|
||||
|
|
|
|||
|
|
@ -18,62 +18,62 @@ from make_post_sell.models.product import get_all_products
|
|||
|
||||
def fix_product_s3_acls(env, dry_run=True):
|
||||
"""Fix S3 ACLs for all products based on their visibility settings."""
|
||||
|
||||
request = env['request']
|
||||
|
||||
request = env["request"]
|
||||
dbsession = request.dbsession
|
||||
|
||||
|
||||
# Get S3 client and bucket name
|
||||
s3_client = request.secure_uploads_client
|
||||
bucket_name = request.app["bucket.secure_uploads"]
|
||||
|
||||
|
||||
# Get all products
|
||||
products = get_all_products(dbsession).all()
|
||||
|
||||
|
||||
print(f"Found {len(products)} products to process")
|
||||
print(f"Bucket: {bucket_name}")
|
||||
print(f"Dry run: {dry_run}")
|
||||
print("-" * 50)
|
||||
|
||||
|
||||
processed = 0
|
||||
errors = 0
|
||||
|
||||
|
||||
for product in products:
|
||||
try:
|
||||
print(f"Processing product {product.id} ({product.title})")
|
||||
print(f" Visibility: {product.human_visibility} ({product.visibility})")
|
||||
|
||||
|
||||
# Check which files exist for this product
|
||||
existing_files = []
|
||||
for file_key in product.file_keys:
|
||||
if file_key in product.extensions:
|
||||
existing_files.append(file_key)
|
||||
|
||||
|
||||
if not existing_files:
|
||||
print(f" No files found, skipping")
|
||||
continue
|
||||
|
||||
|
||||
print(f" Files: {existing_files}")
|
||||
|
||||
|
||||
# Show what ACLs would be applied
|
||||
for file_key in existing_files:
|
||||
acl = product.get_s3_acl_for_file_key(file_key)
|
||||
print(f" {file_key}: {acl}")
|
||||
|
||||
|
||||
if not dry_run:
|
||||
# Actually update the ACLs
|
||||
product.update_s3_acls(s3_client, bucket_name)
|
||||
print(f" ✓ Updated ACLs")
|
||||
else:
|
||||
print(f" (Dry run - no changes made)")
|
||||
|
||||
|
||||
processed += 1
|
||||
|
||||
|
||||
except Exception as e:
|
||||
print(f" ✗ Error processing product {product.id}: {e}")
|
||||
errors += 1
|
||||
|
||||
|
||||
print()
|
||||
|
||||
|
||||
print("-" * 50)
|
||||
print(f"Summary:")
|
||||
print(f" Processed: {processed}")
|
||||
|
|
@ -83,13 +83,18 @@ def fix_product_s3_acls(env, dry_run=True):
|
|||
|
||||
def main():
|
||||
"""Main entry point."""
|
||||
parser = argparse.ArgumentParser(description='Fix S3 ACLs for products based on visibility')
|
||||
parser.add_argument('config_uri', help='Configuration file (e.g., development.ini)')
|
||||
parser.add_argument('--execute', action='store_true',
|
||||
help='Actually make changes (default is dry run)')
|
||||
|
||||
parser = argparse.ArgumentParser(
|
||||
description="Fix S3 ACLs for products based on visibility"
|
||||
)
|
||||
parser.add_argument("config_uri", help="Configuration file (e.g., development.ini)")
|
||||
parser.add_argument(
|
||||
"--execute",
|
||||
action="store_true",
|
||||
help="Actually make changes (default is dry run)",
|
||||
)
|
||||
|
||||
args = parser.parse_args()
|
||||
|
||||
|
||||
# Bootstrap the Pyramid application
|
||||
with bootstrap(args.config_uri) as env:
|
||||
try:
|
||||
|
|
@ -102,5 +107,5 @@ def main():
|
|||
sys.exit(1)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ def setup_models(dbsession, settings):
|
|||
settings["app.root_domain"],
|
||||
"000-000-0000",
|
||||
"none",
|
||||
"Reserved shop for SaaS root domain."
|
||||
"Reserved shop for SaaS root domain.",
|
||||
)
|
||||
root_domain_shop.domain_name = settings["app.root_domain"]
|
||||
|
||||
|
|
@ -28,8 +28,7 @@ def setup_models(dbsession, settings):
|
|||
dbsession.flush()
|
||||
|
||||
root_domain_owner = get_or_create_user_by_email(
|
||||
dbsession,
|
||||
settings["app.root_domain_owner_email"]
|
||||
dbsession, settings["app.root_domain_owner_email"]
|
||||
)
|
||||
|
||||
dbsession.add(root_domain_owner)
|
||||
|
|
@ -44,8 +43,8 @@ def setup_models(dbsession, settings):
|
|||
def parse_args(argv):
|
||||
parser = argparse.ArgumentParser()
|
||||
parser.add_argument(
|
||||
'config_uri',
|
||||
help='Configuration file, e.g., development.ini',
|
||||
"config_uri",
|
||||
help="Configuration file, e.g., development.ini",
|
||||
)
|
||||
return parser.parse_args(argv[1:])
|
||||
|
||||
|
|
@ -60,11 +59,12 @@ def main(argv=sys.argv):
|
|||
models.meta.Base.metadata.create_all(engine)
|
||||
|
||||
try:
|
||||
with env['request'].tm:
|
||||
dbsession = env['request'].dbsession
|
||||
#setup_models(dbsession, settings)
|
||||
with env["request"].tm:
|
||||
dbsession = env["request"].dbsession
|
||||
# setup_models(dbsession, settings)
|
||||
except OperationalError:
|
||||
print('''
|
||||
print(
|
||||
"""
|
||||
Pyramid is having a problem using your SQL database. The problem
|
||||
might be caused by one of the following things:
|
||||
|
||||
|
|
@ -74,4 +74,5 @@ might be caused by one of the following things:
|
|||
2. Your database server may not be running. Check that the
|
||||
database server referred to by the "sqlalchemy.url" setting in
|
||||
your "development.ini" file is running.
|
||||
''')
|
||||
"""
|
||||
)
|
||||
|
|
|
|||
|
|
@ -2,12 +2,12 @@ from .. import models
|
|||
|
||||
|
||||
def setup(env):
|
||||
request = env['request']
|
||||
request = env["request"]
|
||||
|
||||
# start a transaction
|
||||
request.tm.begin()
|
||||
|
||||
# inject some vars into the shell builtins
|
||||
env['tm'] = request.tm
|
||||
env['dbsession'] = request.dbsession
|
||||
env['models'] = models
|
||||
env["tm"] = request.tm
|
||||
env["dbsession"] = request.dbsession
|
||||
env["models"] = models
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -14,6 +14,7 @@ def user_required(
|
|||
max_redirects=3, # Limit the number of redirects
|
||||
):
|
||||
"""This view requires that the request has a user."""
|
||||
|
||||
def wrapped(fn):
|
||||
def inner(request):
|
||||
if request.user and request.user.authenticated:
|
||||
|
|
@ -24,7 +25,9 @@ def user_required(
|
|||
redirect_count = request.session.get("redirect_count", 0)
|
||||
if redirect_count >= max_redirects:
|
||||
# Redirect to a safe default page if max redirects reached
|
||||
request.session.flash(("Too many redirects, please try again later.", "error"))
|
||||
request.session.flash(
|
||||
("Too many redirects, please try again later.", "error")
|
||||
)
|
||||
return HTTPFound(request.route_url("home"))
|
||||
# Increment redirect count
|
||||
request.session["redirect_count"] = redirect_count + 1
|
||||
|
|
@ -34,9 +37,12 @@ def user_required(
|
|||
if redirect_to_route_name:
|
||||
return HTTPFound(request.route_url(redirect_to_route_name))
|
||||
return HTTPFound(get_referer_or_home(request))
|
||||
|
||||
return inner
|
||||
|
||||
return wrapped
|
||||
|
||||
|
||||
# view decorator.
|
||||
def shop_is_ready_required(
|
||||
flash_msg="Sorry, this shop is not ready to make sales yet. Please try again later.",
|
||||
|
|
|
|||
|
|
@ -472,6 +472,7 @@ def cart_checkout(request):
|
|||
xmr_processor_enabled = False
|
||||
if request.monero_enabled:
|
||||
from ..models.crypto_processor import CryptoProcessor
|
||||
|
||||
xmr_processor = (
|
||||
request.dbsession.query(CryptoProcessor)
|
||||
.filter(
|
||||
|
|
|
|||
|
|
@ -26,44 +26,52 @@ def comment_new(request):
|
|||
product_id = request.params.get("product_id")
|
||||
parent_id = request.params.get("parent_id") # For replies
|
||||
data = request.params.get("data", "").strip()
|
||||
|
||||
|
||||
if not product_id or not data:
|
||||
request.session.flash(("Comment content is required", "error"))
|
||||
return HTTPFound(location=get_referer_or_home(request))
|
||||
|
||||
|
||||
# Get product and validate
|
||||
product = get_product_by_id(request.dbsession, product_id)
|
||||
if not product:
|
||||
return HTTPNotFound("Product not found")
|
||||
|
||||
|
||||
shop = product.shop
|
||||
|
||||
|
||||
# Check if user can comment
|
||||
can_comment, error_msg = True, None
|
||||
|
||||
|
||||
if not shop.comments_enabled:
|
||||
can_comment, error_msg = False, "Comments are disabled for this shop"
|
||||
elif shop.comments_require_purchase:
|
||||
# Check if user has purchased this product
|
||||
from ..models.user_product import UserProduct
|
||||
user_product = request.dbsession.query(UserProduct).filter(
|
||||
UserProduct.user_id == request.user.id,
|
||||
UserProduct.product_id == product_id
|
||||
).first()
|
||||
|
||||
|
||||
user_product = (
|
||||
request.dbsession.query(UserProduct)
|
||||
.filter(
|
||||
UserProduct.user_id == request.user.id,
|
||||
UserProduct.product_id == product_id,
|
||||
)
|
||||
.first()
|
||||
)
|
||||
|
||||
if not user_product:
|
||||
can_comment, error_msg = False, "You must purchase this product to leave a comment"
|
||||
|
||||
can_comment, error_msg = (
|
||||
False,
|
||||
"You must purchase this product to leave a comment",
|
||||
)
|
||||
|
||||
if not can_comment:
|
||||
request.session.flash((error_msg, "error"))
|
||||
return HTTPFound(location=get_referer_or_home(request))
|
||||
|
||||
|
||||
# Create comment
|
||||
comment = Comment()
|
||||
comment.product_id = product_id
|
||||
comment.user_id = request.user.id
|
||||
comment.set_data(data)
|
||||
|
||||
|
||||
# Set approval status based on shop settings
|
||||
if shop.comments_require_approval:
|
||||
# Shop owners and editors get auto-approved
|
||||
|
|
@ -74,7 +82,7 @@ def comment_new(request):
|
|||
else:
|
||||
# No approval required
|
||||
comment.approved = True
|
||||
|
||||
|
||||
# Handle reply (set parent and root)
|
||||
if parent_id:
|
||||
parent_comment = get_comment_by_id(request.dbsession, parent_id)
|
||||
|
|
@ -86,15 +94,15 @@ def comment_new(request):
|
|||
# Root comment
|
||||
comment.root_id = comment.id
|
||||
comment.graph_depth = 0
|
||||
|
||||
|
||||
request.dbsession.add(comment)
|
||||
request.dbsession.flush()
|
||||
|
||||
|
||||
if comment.approved:
|
||||
request.session.flash(("Comment posted successfully", "success"))
|
||||
else:
|
||||
request.session.flash(("Comment submitted for approval", "success"))
|
||||
|
||||
|
||||
# Redirect to the product page with fragment to scroll to the new comment
|
||||
product_url = product.absolute_url(request)
|
||||
return HTTPFound(location=f"{product_url}#comment-{comment.id}")
|
||||
|
|
@ -106,18 +114,18 @@ def comment_reply_get(request):
|
|||
"""Show reply to comment form."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
parent_comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not parent_comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check if user can reply
|
||||
shop = parent_comment.product.shop
|
||||
can_comment, error_msg = parent_comment.can_user_comment(request.user, shop)
|
||||
|
||||
|
||||
if not can_comment:
|
||||
request.session.flash((error_msg, "error"))
|
||||
return HTTPFound(location=parent_comment.product.absolute_url(request))
|
||||
|
||||
|
||||
return {
|
||||
"parent_comment": parent_comment,
|
||||
"product": parent_comment.product,
|
||||
|
|
@ -131,24 +139,26 @@ def comment_reply_post(request):
|
|||
"""Create a reply to a comment."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
parent_comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not parent_comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check if user can reply
|
||||
shop = parent_comment.product.shop
|
||||
can_comment, error_msg = parent_comment.can_user_comment(request.user, shop)
|
||||
|
||||
|
||||
if not can_comment:
|
||||
request.session.flash((error_msg, "error"))
|
||||
return HTTPFound(location=parent_comment.product.absolute_url(request))
|
||||
|
||||
|
||||
data = request.params.get("data", "").strip()
|
||||
|
||||
|
||||
if not data:
|
||||
request.session.flash(("Comment content is required", "error"))
|
||||
return HTTPFound(location=request.route_url("comment_reply", comment_id=comment_id))
|
||||
|
||||
return HTTPFound(
|
||||
location=request.route_url("comment_reply", comment_id=comment_id)
|
||||
)
|
||||
|
||||
# Create reply comment
|
||||
comment = Comment()
|
||||
comment.product_id = parent_comment.product_id
|
||||
|
|
@ -157,7 +167,7 @@ def comment_reply_post(request):
|
|||
comment.root_id = parent_comment.root_id or parent_comment.id
|
||||
comment.set_data(data)
|
||||
comment.recompute_depth()
|
||||
|
||||
|
||||
# Set approval status based on shop settings
|
||||
if shop.comments_require_approval:
|
||||
# Shop owners and editors get auto-approved
|
||||
|
|
@ -168,15 +178,15 @@ def comment_reply_post(request):
|
|||
else:
|
||||
# No approval required
|
||||
comment.approved = True
|
||||
|
||||
|
||||
request.dbsession.add(comment)
|
||||
request.dbsession.flush()
|
||||
|
||||
|
||||
if comment.approved:
|
||||
request.session.flash(("Reply posted successfully", "success"))
|
||||
else:
|
||||
request.session.flash(("Reply submitted for approval", "success"))
|
||||
|
||||
|
||||
# Redirect to the product page with fragment to scroll to the new comment
|
||||
product_url = parent_comment.product.absolute_url(request)
|
||||
return HTTPFound(location=f"{product_url}#comment-{comment.id}")
|
||||
|
|
@ -188,15 +198,17 @@ def comment_edit_get(request):
|
|||
"""Show edit comment form."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check permissions
|
||||
shop = comment.product.shop
|
||||
if comment.user_id != request.user.id and not comment.can_user_moderate(request.user, shop):
|
||||
if comment.user_id != request.user.id and not comment.can_user_moderate(
|
||||
request.user, shop
|
||||
):
|
||||
return HTTPForbidden("You can only edit your own comments")
|
||||
|
||||
|
||||
return {
|
||||
"comment": comment,
|
||||
"product": comment.product,
|
||||
|
|
@ -210,24 +222,28 @@ def comment_edit_post(request):
|
|||
"""Update a comment."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check permissions
|
||||
shop = comment.product.shop
|
||||
if comment.user_id != request.user.id and not comment.can_user_moderate(request.user, shop):
|
||||
if comment.user_id != request.user.id and not comment.can_user_moderate(
|
||||
request.user, shop
|
||||
):
|
||||
return HTTPForbidden("You can only edit your own comments")
|
||||
|
||||
|
||||
data = request.params.get("data", "").strip()
|
||||
|
||||
|
||||
if not data:
|
||||
request.session.flash(("Comment content is required", "error"))
|
||||
return HTTPFound(location=request.route_url("comment_edit", comment_id=comment_id))
|
||||
|
||||
return HTTPFound(
|
||||
location=request.route_url("comment_edit", comment_id=comment_id)
|
||||
)
|
||||
|
||||
comment.set_data(data)
|
||||
request.session.flash(("Comment updated successfully", "success"))
|
||||
|
||||
|
||||
# Redirect back to product page with fragment to scroll to the edited comment
|
||||
product_url = comment.product.absolute_url(request)
|
||||
return HTTPFound(location=f"{product_url}#comment-{comment.id}")
|
||||
|
|
@ -239,20 +255,22 @@ def comment_delete(request):
|
|||
"""Delete a comment."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check permissions
|
||||
shop = comment.product.shop
|
||||
if comment.user_id != request.user.id and not comment.can_user_moderate(request.user, shop):
|
||||
if comment.user_id != request.user.id and not comment.can_user_moderate(
|
||||
request.user, shop
|
||||
):
|
||||
return HTTPForbidden("You can only delete your own comments")
|
||||
|
||||
|
||||
product_url = comment.product.absolute_url(request)
|
||||
|
||||
|
||||
# Soft delete using disable method
|
||||
comment.disable()
|
||||
|
||||
|
||||
request.session.flash(("Comment deleted successfully", "success"))
|
||||
return HTTPFound(location=product_url)
|
||||
|
||||
|
|
@ -263,18 +281,18 @@ def comment_approve(request):
|
|||
"""Approve a comment (shop owners and editors only)."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check permissions - shop owners and editors can approve
|
||||
shop = comment.product.shop
|
||||
if not comment.can_user_moderate(request.user, shop):
|
||||
return HTTPForbidden("Only shop owners and editors can approve comments")
|
||||
|
||||
|
||||
comment.approved = True
|
||||
comment.stamp_updated_timestamp()
|
||||
|
||||
|
||||
request.session.flash(("Comment approved", "success"))
|
||||
return HTTPFound(location=get_referer_or_home(request))
|
||||
|
||||
|
|
@ -285,18 +303,18 @@ def comment_unapprove(request):
|
|||
"""Unapprove a comment (shop owners and editors only)."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check permissions - shop owners and editors can unapprove
|
||||
shop = comment.product.shop
|
||||
if not comment.can_user_moderate(request.user, shop):
|
||||
return HTTPForbidden("Only shop owners and editors can moderate comments")
|
||||
|
||||
|
||||
comment.approved = False
|
||||
comment.stamp_updated_timestamp()
|
||||
|
||||
|
||||
request.session.flash(("Comment unapproved", "success"))
|
||||
return HTTPFound(location=get_referer_or_home(request))
|
||||
|
||||
|
|
@ -307,17 +325,21 @@ def comment_undelete(request):
|
|||
"""Undelete a comment (shop owners and editors only)."""
|
||||
comment_id = request.matchdict["comment_id"]
|
||||
comment = get_comment_by_id(request.dbsession, comment_id)
|
||||
|
||||
|
||||
if not comment:
|
||||
return HTTPNotFound("Comment not found")
|
||||
|
||||
|
||||
# Check permissions - comment owner, shop owners, or shop editors can undelete
|
||||
shop = comment.product.shop
|
||||
if comment.user_id != request.user.uuid_str and not (shop.is_owner(request.user) or shop.is_editor(request.user)):
|
||||
return HTTPForbidden("Only comment owners, shop owners, and shop editors can undelete comments")
|
||||
|
||||
if comment.user_id != request.user.uuid_str and not (
|
||||
shop.is_owner(request.user) or shop.is_editor(request.user)
|
||||
):
|
||||
return HTTPForbidden(
|
||||
"Only comment owners, shop owners, and shop editors can undelete comments"
|
||||
)
|
||||
|
||||
# Re-enable the comment
|
||||
comment.enable()
|
||||
|
||||
|
||||
request.session.flash(("Comment restored successfully", "success"))
|
||||
return HTTPFound(location=comment.product.absolute_url(request))
|
||||
return HTTPFound(location=comment.product.absolute_url(request))
|
||||
|
|
|
|||
|
|
@ -67,11 +67,9 @@ def content(request):
|
|||
|
||||
# Load comments for the content
|
||||
from ..models.comment import get_comments_for_product
|
||||
|
||||
comments = get_comments_for_product(
|
||||
request.dbsession,
|
||||
product.id,
|
||||
shop=product.shop,
|
||||
user=request.user
|
||||
request.dbsession, product.id, shop=product.shop, user=request.user
|
||||
)
|
||||
|
||||
return {
|
||||
|
|
|
|||
|
|
@ -71,13 +71,23 @@ def crypto_processor_settings(request):
|
|||
|
||||
client = get_client_from_settings(request.registry.settings)
|
||||
|
||||
# Create new account with shop name as label
|
||||
account_label = f"shop_{shop.name[:20]}_{shop.id[:8]}"
|
||||
# Create new account with shop UUID as label
|
||||
account_label = f"mps-shop-{shop.uuid_str}"
|
||||
result = client._call("create_account", {"label": account_label})
|
||||
account_index = result.get("account_index")
|
||||
|
||||
if account_index is not None:
|
||||
processor.wallet_label = str(account_index)
|
||||
|
||||
# Tag the account with the shop name for easier identification
|
||||
try:
|
||||
client._call(
|
||||
"tag_accounts",
|
||||
{"tag": shop.name, "accounts": [account_index]},
|
||||
)
|
||||
except Exception as tag_error:
|
||||
# Don't fail account creation if tagging fails
|
||||
pass
|
||||
else:
|
||||
raise Exception("Failed to get account_index from create_account")
|
||||
|
||||
|
|
|
|||
|
|
@ -51,8 +51,12 @@ def ask_for_on_demand_tls(request):
|
|||
"""
|
||||
domain_name_requesting_tls = request.params.get("domain")
|
||||
if domain_name_requesting_tls:
|
||||
query = text("SELECT EXISTS (SELECT 1 FROM mps_shop WHERE domain_name = :domain_name)")
|
||||
result = request.dbsession.execute(query, {'domain_name': domain_name_requesting_tls})
|
||||
query = text(
|
||||
"SELECT EXISTS (SELECT 1 FROM mps_shop WHERE domain_name = :domain_name)"
|
||||
)
|
||||
result = request.dbsession.execute(
|
||||
query, {"domain_name": domain_name_requesting_tls}
|
||||
)
|
||||
exists = result.scalar()
|
||||
if exists:
|
||||
return Response(status=200)
|
||||
|
|
|
|||
|
|
@ -84,13 +84,11 @@ def product(request):
|
|||
if product.has_product_file:
|
||||
product_size = product.human_product_file_bytes
|
||||
|
||||
# Load comments for the product
|
||||
# Load comments for the product
|
||||
from ..models.comment import get_comments_for_product
|
||||
|
||||
comments = get_comments_for_product(
|
||||
request.dbsession,
|
||||
product.id,
|
||||
shop=product.shop,
|
||||
user=request.user
|
||||
request.dbsession, product.id, shop=product.shop, user=request.user
|
||||
)
|
||||
|
||||
return {
|
||||
|
|
@ -248,7 +246,11 @@ def product_edit(request):
|
|||
|
||||
if visibility != product.visibility:
|
||||
product_modified = True
|
||||
product.set_visibility(visibility, request.secure_uploads_client, request.app["bucket.secure_uploads"])
|
||||
product.set_visibility(
|
||||
visibility,
|
||||
request.secure_uploads_client,
|
||||
request.app["bucket.secure_uploads"],
|
||||
)
|
||||
request.session.flash(("You updated the product's visibility.", "success"))
|
||||
|
||||
if price != product.price:
|
||||
|
|
|
|||
|
|
@ -150,19 +150,19 @@ def shop_location_form(request):
|
|||
"hours_open": shop_location.hours_open if shop_location else "",
|
||||
"local_pickup": shop_location.local_pickup if shop_location else False,
|
||||
"local_delivery": shop_location.local_delivery if shop_location else False,
|
||||
"local_delivery_rate": shop_location.local_delivery_rate
|
||||
if shop_location
|
||||
else "0.00",
|
||||
"local_delivery_rate": (
|
||||
shop_location.local_delivery_rate if shop_location else "0.00"
|
||||
),
|
||||
"local_shipping": shop_location.local_shipping if shop_location else False,
|
||||
"local_shipping_rate": shop_location.local_shipping_rate
|
||||
if shop_location
|
||||
else "0.00",
|
||||
"international_shipping": shop_location.international_shipping
|
||||
if shop_location
|
||||
else False,
|
||||
"international_shipping_rate": shop_location.international_shipping_rate
|
||||
if shop_location
|
||||
else "0.00",
|
||||
"local_shipping_rate": (
|
||||
shop_location.local_shipping_rate if shop_location else "0.00"
|
||||
),
|
||||
"international_shipping": (
|
||||
shop_location.international_shipping if shop_location else False
|
||||
),
|
||||
"international_shipping_rate": (
|
||||
shop_location.international_shipping_rate if shop_location else "0.00"
|
||||
),
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ from . import user_required
|
|||
def get_enabled_coins(request):
|
||||
"""Get list of enabled cryptocurrency types from all shops."""
|
||||
from ..models.crypto_processor import CryptoProcessor
|
||||
|
||||
|
||||
# Get distinct coin types from all enabled crypto processors
|
||||
enabled_coins = (
|
||||
request.dbsession.query(CryptoProcessor.coin_type)
|
||||
|
|
@ -19,7 +19,7 @@ def get_enabled_coins(request):
|
|||
.distinct()
|
||||
.all()
|
||||
)
|
||||
|
||||
|
||||
# Return list of coin type strings
|
||||
return [coin_type for (coin_type,) in enabled_coins]
|
||||
|
||||
|
|
|
|||
2
setup.py
2
setup.py
|
|
@ -1,6 +1,7 @@
|
|||
import os
|
||||
from setuptools import setup, find_packages
|
||||
|
||||
|
||||
def parse_requirements(filename):
|
||||
"""
|
||||
Read and parse a requirements file, ignoring comments and blank lines.
|
||||
|
|
@ -10,6 +11,7 @@ def parse_requirements(filename):
|
|||
lines = f.read().splitlines()
|
||||
return [line.strip() for line in lines if line.strip() and not line.startswith("#")]
|
||||
|
||||
|
||||
# Determine the runtime requirements.
|
||||
install_requires = parse_requirements("requirements.py3.txt")
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue