def delete_unwanted_existing_product(isbn: str): product_has_at_least_one_booking = (Product.query.filter_by( idAtProviders=isbn).join(Offer).join(Stock).join(Booking).count() > 0) product = find_active_book_product_by_isbn(isbn) if not product: return if product_has_at_least_one_booking: offers = get_offers_by_product_id(product.id) product.isGcuCompatible = False offers = update_is_active_status(offers, False) repository.save(*offers, product) raise ProductWithBookingsException objects_to_delete = [] objects_to_delete.append(product) offers = get_offers_by_product_id(product.id) offer_ids = [offer.id for offer in offers] objects_to_delete = objects_to_delete + offers stocks = offers_repository.get_stocks_for_offers(offer_ids) objects_to_delete = objects_to_delete + stocks mediations = get_mediations_for_offers(offer_ids) objects_to_delete = objects_to_delete + mediations favorites = get_favorites_for_offers(offer_ids) objects_to_delete = objects_to_delete + favorites repository.delete(*objects_to_delete)
def test_when_no_deposit(self): # given user = UserFactory() repository.delete(*user.deposits) # then assert user.deposit_version == None
def change_user_email(token: str) -> None: try: jwt_payload = decode_jwt_token(token) except ( ExpiredSignatureError, InvalidSignatureError, DecodeError, InvalidTokenError, ) as error: raise InvalidTokenError() from error if not {"exp", "new_email", "current_email"} <= set(jwt_payload): raise InvalidTokenError() new_email = jwt_payload["new_email"] if User.query.filter_by(email=new_email).first(): return current_email = jwt_payload["current_email"] current_user = User.query.filter_by(email=current_email).first() if not current_user: return current_user.email = new_email sessions = UserSession.query.filter_by(userId=current_user.id) repository.delete(*sessions) repository.save(current_user) return
def change_user_email(token: str) -> None: try: jwt_payload = decode_jwt_token(token) except ( ExpiredSignatureError, InvalidSignatureError, DecodeError, InvalidTokenError, ) as error: raise InvalidTokenError() from error if not {"exp", "new_email", "current_email"} <= set(jwt_payload): raise InvalidTokenError() new_email = sanitize_email(jwt_payload["new_email"]) if find_user_by_email(new_email): return current_user = find_user_by_email(jwt_payload["current_email"]) if not current_user: return current_user.email = new_email sessions = UserSession.query.filter_by(userId=current_user.id) repository.delete(*sessions) repository.save(current_user) logger.info("User has changed their email", extra={"user": current_user.id}) return
def test_balance_is_0_with_no_deposits_and_no_bookings(self): # given user = factories.UserFactory() repository.delete(user.deposit) # then assert user.wallet_balance == 0 assert user.real_wallet_balance == 0
def delete_favorite(offer_id): dehumanized_offer_id = dehumanize(offer_id) favorite = find_favorite_for_offer_and_user(dehumanized_offer_id, current_user.id).first_or_404() repository.delete(favorite) return jsonify(as_dict(favorite)), 200
def create_mediation_v2( user: User, offer: Offer, credit: str, image_as_bytes: bytes, crop_params: tuple = None, ) -> Mediation: # checks image type, min dimensions validation.check_image(image_as_bytes) existing_mediations = mediation_queries.get_mediations_for_offers( [offer.id]) mediation = Mediation( author=user, offer=offer, credit=credit, ) # `create_thumb()` requires the object to have an id, so we must save now. repository.save(mediation) try: # TODO(fseguin): cleanup after image upload v2 launch create_thumb(mediation, image_as_bytes, image_index=0, crop_params=crop_params, use_v2=True) except Exception as exc: app.logger.exception( "An unexpected error was encountered during the thumbnail creation: %s", exc) # I could not use savepoints and rollbacks with SQLA repository.delete(mediation) raise ThumbnailStorageError else: mediation.thumbCount = 1 repository.save(mediation) # cleanup former thumbnails and mediations for previous_mediation in existing_mediations: try: for thumb_index in range(0, mediation.thumbCount): remove_thumb(previous_mediation, image_index=thumb_index) except Exception as exc: # pylint: disable=broad-except app.logger.exception( "An unexpected error was encountered during the thumbnails deletion for %s: %s", mediation, exc, ) else: repository.delete(previous_mediation) if feature_queries.is_active(FeatureToggle.SYNCHRONIZE_ALGOLIA): redis.add_offer_id(client=app.redis_client, offer_id=offer.id) return mediation
def delete_corrupted_allocine_stocks(): new_stock_id_at_providers_format = "%#%" allocine_provider = get_provider_by_local_class("AllocineStocks") stocks_to_delete = (Stock.query.filter_by( lastProviderId=allocine_provider.id ).filter_by(isSoftDeleted=True).filter( Stock.idAtProviders.notilike(new_stock_id_at_providers_format)).all()) repository.delete(*stocks_to_delete)
def _delete_user_offerers_from_rows(csv_rows: Iterable) -> None: user_offerers_successful = [] user_offerers_in_error = [] csv_rows_iterable = iter(csv_rows) headers = next(csv_rows_iterable) for row in csv_rows_iterable: if _is_blank_row(row): continue row = dict(zip(headers, row)) user_id = row[USER_ID_COLUMN_HEADER] offerer_id = row[OFFERER_ID_COLUMN_HEADER] user_offerer = find_one_or_none_by_user_id_and_offerer_id( int(user_id), int(offerer_id)) if user_offerer is None: continue user_offerer_id = user_offerer.id logger.info( "[DELETE USER_OFFERERS FROM FILE] Suppression du rattachement pour le user d'id %s et l'offerer " "d'id %s est lancée", user_id, offerer_id, ) try: repository.delete(user_offerer) logger.info( "[DELETE USER_OFFERERS FROM FILE] Suppression du rattachement pour le user d'id %s et l'offerer " "d'id %s réussie", user_id, offerer_id, ) user_offerers_successful.append(user_offerer_id) except ApiErrors as error: logger.exception( "[DELETE USER_OFFERERS FROM FILE] %s pour le rattachement avec le user d'id %s et l'offerer d'id %s", error.errors, user_id, offerer_id, ) user_offerers_in_error.append(user_offerer_id) logger.info("[DELETE USER_OFFERERS FROM FILE] %i RATTACHEMENT SUPPRIMES", len(user_offerers_successful)) logger.info( "[DELETE USER_OFFERERS FROM FILE] LISTE DES RATTACHEMENT SUPPRIMES") logger.info(user_offerers_successful) if len(user_offerers_in_error) > 0: logger.error( "[DELETE USER_OFFERERS FROM FILE] LISTE DES RATTACHEMENTS EN ERREUR" ) logger.error(user_offerers_in_error)
def create_mediation( user: User, offer: Offer, credit: str, image_as_bytes: bytes, crop_params: tuple = None, ) -> Mediation: # checks image type, min dimensions validation.check_image(image_as_bytes) mediation = Mediation( author=user, offer=offer, credit=credit, ) # `create_thumb()` requires the object to have an id, so we must save now. repository.save(mediation) try: create_thumb(mediation, image_as_bytes, image_index=0, crop_params=crop_params) except Exception as exc: logger.exception( "An unexpected error was encountered during the thumbnail creation: %s", exc) # I could not use savepoints and rollbacks with SQLA repository.delete(mediation) raise ThumbnailStorageError else: mediation.thumbCount = 1 repository.save(mediation) # cleanup former thumbnails and mediations previous_mediations = (Mediation.query.filter( Mediation.offerId == offer.id).filter( Mediation.id != mediation.id).all()) for previous_mediation in previous_mediations: try: for thumb_index in range(0, previous_mediation.thumbCount): remove_thumb(previous_mediation, image_index=thumb_index) except Exception as exc: # pylint: disable=broad-except logger.exception( "An unexpected error was encountered during the thumbnails deletion for %s: %s", mediation, exc, ) else: repository.delete(previous_mediation) search.async_index_offer_ids([offer.id]) return mediation
def change_pro_users_to_beneficiary(pro_users_ids: List[int]) -> None: users = User.query.filter(User.id.in_(pro_users_ids)).all() maximum_wallet_balance = 500 for user in users: user.isBeneficiary = True user.needsToFillCulturalSurvey = True deposit = create_deposit(user, amount=maximum_wallet_balance) repository.save(user, deposit) user_offerer = UserOfferer.query.filter_by(user=user).all() repository.delete(*user_offerer)
def change_pro_users_to_beneficiary(pro_users_ids: list[int]) -> None: users = User.query.filter(User.id.in_(pro_users_ids)).all() for user in users: user.add_beneficiary_role() user.remove_pro_role() user.needsToFillCulturalSurvey = True deposit = payments_api.create_deposit(user, "public") repository.save(user, deposit) user_offerer = UserOfferer.query.filter_by(user=user).all() repository.delete(*user_offerer)
def test_deposit_created_with_an_expiration_date(self, app): # Given beneficiary = UserFactory(email="*****@*****.**") repository.delete(*beneficiary.deposits) # When deposit = create_deposit(beneficiary, "created by test") # Then assert deposit.expirationDate == datetime(2023, 2, 5, 9, 0, 0)
def test_users_with_no_deposits_are_ignored(self): # given user1 = users_factories.BeneficiaryGrant18Factory() user2 = users_factories.BeneficiaryGrant18Factory() repository.delete(user2.deposit) # when balances = get_all_users_wallet_balances() # then assert len(balances) == 1 assert balances[0].user_id == user1.id
def suspend_account(user: User, reason: constants.SuspensionReason, actor: User) -> None: user.isActive = False user.suspensionReason = str(reason) # If we ever unsuspend the account, we'll have to explictly enable # isAdmin again. An admin now may not be an admin later. user.isAdmin = False user.setPassword(secrets.token_urlsafe(30)) repository.save(user) sessions = UserSession.query.filter_by(userId=user.id) repository.delete(*sessions) logger.info("user=%s has been suspended by actor=%s for reason=%s", user.id, actor.id, reason)
def delete_venue_and_offers_for_venue_id(humanized_venue_id: str): dehumanized_venue_id = dehumanize(humanized_venue_id) offers = get_offers_by_venue_id(dehumanized_venue_id) venue = find_by_id(dehumanized_venue_id) if any(offer.stocks for offer in offers): raise AttributeError( "Offres non supprimables car au moins une contient des stocks") for offer in offers: repository.delete(offer) if venue: repository.delete(venue)
def test_delete_user_when_she_has_no_deposit(): admin = users_factories.AdminFactory() user_without_deposit = users_factories.UserFactory( email="*****@*****.**") users_factories.FavoriteFactory(user=user_without_deposit) fraud_factories.BeneficiaryFraudCheckFactory(user=user_without_deposit) fraud_factories.BeneficiaryFraudResultFactory(user=user_without_deposit) fraud_factories.BeneficiaryFraudReviewFactory(user=user_without_deposit, author=admin) deposit = Deposit.query.all() repository.delete(*deposit) suspend_or_delete_from_file( "tests/scripts/beneficiary/users_to_delete_fixture.txt", admin.email, ) assert User.query.all() == [admin]
def when_user_is_logged_in_and_has_no_deposit(self, app): # Given user = BeneficiaryGrant18Factory( email="*****@*****.**", postalCode="93020", ) repository.delete(*user.deposits) # When response = (TestClient(app.test_client()).with_session_auth( email="*****@*****.**").get("/beneficiaries/current")) # Then assert response.status_code == 200 assert response.json == { "activity": user.activity, "address": user.address, "city": user.city, "civility": user.civility, "dateCreated": format_into_utc_date(user.dateCreated), "dateOfBirth": format_into_utc_date(user.dateOfBirth), "departementCode": user.departementCode, "deposit_expiration_date": None, "deposit_version": None, "domainsCredit": None, "email": "*****@*****.**", "firstName": user.firstName, "hasPhysicalVenues": user.hasPhysicalVenues, "id": humanize(user.id), "isActive": True, "isAdmin": False, "isBeneficiary": True, "isEmailValidated": True, "lastName": user.lastName, "needsToFillCulturalSurvey": True, "needsToSeeTutorials": True, "pk": user.id, "phoneNumber": user.phoneNumber, "postalCode": user.postalCode, "publicName": user.publicName, "roles": ["BENEFICIARY"], "suspensionReason": "", "wallet_balance": 0.0, "wallet_is_activated": False, }
def suspend_account(user: User, reason: constants.SuspensionReason, actor: User) -> dict[str, int]: import pcapi.core.bookings.api as bookings_api # avoid import loop user.isActive = False user.suspensionReason = str(reason) user.remove_admin_role() user.setPassword(secrets.token_urlsafe(30)) repository.save(user) sessions = UserSession.query.filter_by(userId=user.id) repository.delete(*sessions) n_bookings = 0 # Cancel all bookings of the related offerer if the suspended # account was the last active offerer's account. if reason == constants.SuspensionReason.FRAUD: for offerer in user.offerers: if any(u.isActive and u != user for u in offerer.users): continue bookings = bookings_repository.find_cancellable_bookings_by_offerer(offerer.id) for booking in bookings: bookings_api.cancel_booking_for_fraud(booking) n_bookings += 1 # Cancel all bookings of the user (the following works even if the # user is not a beneficiary). cancel_booking_callback = { constants.SuspensionReason.FRAUD: bookings_api.cancel_booking_for_fraud, constants.SuspensionReason.UPON_USER_REQUEST: bookings_api.cancel_booking_on_user_requested_account_suspension, }.get(reason) if cancel_booking_callback: for booking in bookings_repository.find_cancellable_bookings_by_beneficiaries([user]): cancel_booking_callback(booking) n_bookings += 1 logger.info( "Account has been suspended", extra={ "actor": actor.id, "user": user.id, "reason": str(reason), }, ) return {"cancelled_bookings": n_bookings}
def when_user_is_logged_in_and_has_no_deposit(self, app): # Given user = UserFactory( email="*****@*****.**", postalCode="93020", ) repository.delete(*user.deposits) # When response = TestClient(app.test_client()).with_auth(email="*****@*****.**").get("/beneficiaries/current") # Then assert response.status_code == 200 json = response.json assert json["email"] == "*****@*****.**" assert json["expenses"] == [] assert "password" not in json assert "clearTextPassword" not in json assert "resetPasswordToken" not in json assert "resetPasswordTokenValidityLimit" not in json assert json["wallet_is_activated"] == False
def delete_venue_from_iris_venues(venue_id: int) -> None: iris_venues_to_delete = IrisVenues.query.filter_by(venueId=venue_id).all() repository.delete(*iris_venues_to_delete)
def delete_user_session(user_id: int, session_uuid: UUID): session = UserSession.query.filter_by(userId=user_id, uuid=session_uuid).one_or_none() if session: repository.delete(session)