prompt: You will be provided with a partial code base and an issue statement explaining a problem to resolve.
  <issue>
  Кастомные теги в мейлчимпе
  Чтобы можно было в лид-магните указать теги, которые пробрасываются в аудиторию мейлчимпа
  
  </issue>
  <code>
  [start of src/magnets/creator.py]
  1 from magnets.models import EmailLeadMagnetCampaign, LeadCampaignLogEntry
  2 from users.creator import UserCreator
  3 from users.models import User
  4 
  5 
  6 class LeadCreator:
  7     def __init__(self, campaign: EmailLeadMagnetCampaign, email: str, name: str = None):
  8         self.data = {
  9             'name': name,
  10             'email': email,
  11         }
  12 
  13         self.campaign = campaign
  14 
  15     def __call__(self):
  16         self.user = self._create_user()
  17         self._create_log_entry()
  18 
  19         self.campaign.execute(self.user)
  20 
  21     def _create_user(self) -> User:
  22         return UserCreator(
  23             name=self.data['name'],
  24             email=self.data['email'],
  25             subscribe=True,
  26         )()
  27 
  28     def _create_log_entry(self):
  29         LeadCampaignLogEntry.objects.create(
  30             user=self.user,
  31             campaign=self.campaign,
  32         )
  33
  [end of src/magnets/creator.py]
  [start of src/shipping/shipments/course.py]
  1 from typing import Optional
  2 
  3 from app.tasks import invite_to_clickmeeting, invite_to_zoomus, send_mail, subscribe_to_mailchimp
  4 from products.models import Course
  5 from shipping import factory
  6 from shipping.shipments.base import BaseShipment
  7 
  8 
  9 @factory.register(Course)
  10 class CourseShipment(BaseShipment):
  11     @property
  12     def course(self):
  13         return self.stuff_to_ship
  14 
  15     def ship(self):
  16         self.invite_to_clickmeeting()
  17         self.invite_to_zoomus()
  18         self.subscribe_to_mailchimp()
  19 
  20         self.send_welcome_letter()
  21 
  22     def subscribe_to_mailchimp(self):
  23         if self.course.mailchimp_list_id is not None:
  24             subscribe_to_mailchimp.delay(
  25                 list_id=self.course.mailchimp_list_id,
  26                 user_id=self.user.pk,
  27                 tags=[self.course.slug],
  28             )
  29 
  30     def invite_to_clickmeeting(self):
  31         if self.course.clickmeeting_room_url is not None:
  32             invite_to_clickmeeting.delay(
  33                 room_url=self.course.clickmeeting_room_url,
  34                 email=self.user.email,
  35             )
  36 
  37     def invite_to_zoomus(self):
  38         if self.course.zoomus_webinar_id is not None and len(self.course.zoomus_webinar_id):
  39             invite_to_zoomus.delay(
  40                 webinar_id=self.course.zoomus_webinar_id,
  41                 user_id=self.user.id,
  42             )
  43 
  44     def send_welcome_letter(self):
  45         if self.welcome_letter_template_id is not None:
  46             send_mail.delay(
  47                 to=self.user.email,
  48                 template_id=self.welcome_letter_template_id,
  49                 ctx=self.get_template_context(),
  50                 disable_antispam=True,
  51             )
  52 
  53     def get_template_context(self) -> dict:
  54         return {
  55             'name': self.course.name,
  56             'slug': self.course.slug,
  57             'name_genitive': self.course.name_genitive,
  58             **self.get_gift_template_context(),
  59         }
  60 
  61     @property
  62     def welcome_letter_template_id(self) -> Optional[str]:
  63         """Get special gift template letter id if order is a gift and it is present"""
  64         template_id = self.course.welcome_letter_template_id
  65 
  66         if self.order is not None and self.order.giver is not None:  # this is a gift
  67             template_id = self.course.gift_welcome_letter_template_id or self.course.welcome_letter_template_id
  68 
  69         if template_id is None or not len(template_id):  # fuck this null=True in CharFields
  70             return None
  71 
  72         return template_id
  73
  [end of src/shipping/shipments/course.py]
  </code>
  
  I need you to solve this issue by generating a single patch file that I can apply directly to this repository using git apply. Please respond with a single patch file in the following format.
  <patch>
  diff --git a/file.py b/file.py
  --- a/file.py
  +++ b/file.py
  @@ -1,27 +1,35 @@
   def euclidean(a, b):
  -    while b:
  -        a, b = b, a % b
  -    return a
  +    if b == 0:
  +        return a
  +    return euclidean(b, a % b)
   
   
   def bresenham(x0, y0, x1, y1):
       points = []
       dx = abs(x1 - x0)
       dy = abs(y1 - y0)
  -    sx = 1 if x0 < x1 else -1
  -    sy = 1 if y0 < y1 else -1
  -    err = dx - dy
  +    x, y = x0, y0
  +    sx = -1 if x0 > x1 else 1
  +    sy = -1 if y0 > y1 else 1
   
  -    while True:
  -        points.append((x0, y0))
  -        if x0 == x1 and y0 == y1:
  -            break
  -        e2 = 2 * err
  -        if e2 > -dy:
  -            err -= dy
  -            x0 += sx
  -        if e2 < dx:
  -            err += dx
  -            y0 += sy
  +    if dx > dy:
  +        err = dx / 2.0
  +        while x != x1:
  +            points.append((x, y))
  +            err -= dy
  +            if err < 0:
  +                y += sy
  +                err += dx
  +            x += sx
  +    else:
  +        err = dy / 2.0
  +        while y != y1:
  +            points.append((x, y))
  +            err -= dx
  +            if err < 0:
  +                x += sx
  +                err += dy
  +            y += sy
  +
  +    points.append((x, y))
       return points
  
  </patch>
golden_diff: diff --git a/src/magnets/creator.py b/src/magnets/creator.py
  --- a/src/magnets/creator.py
  +++ b/src/magnets/creator.py
  @@ -23,6 +23,7 @@
               name=self.data['name'],
               email=self.data['email'],
               subscribe=True,
  +            tags=self.tags,
           )()
   
       def _create_log_entry(self):
  @@ -30,3 +31,7 @@
               user=self.user,
               campaign=self.campaign,
           )
  +
  +    @property
  +    def tags(self):
  +        return [f'{self.campaign.slug}-lead-magnet']
  diff --git a/src/shipping/shipments/course.py b/src/shipping/shipments/course.py
  --- a/src/shipping/shipments/course.py
  +++ b/src/shipping/shipments/course.py
  @@ -24,7 +24,7 @@
               subscribe_to_mailchimp.delay(
                   list_id=self.course.mailchimp_list_id,
                   user_id=self.user.pk,
  -                tags=[self.course.slug],
  +                tags=[self.course.slug, f'{self.course.slug}-purchased'],
               )
   
       def invite_to_clickmeeting(self):
  
verification_info: {"golden_diff": "diff --git a/src/magnets/creator.py b/src/magnets/creator.py\n--- a/src/magnets/creator.py\n+++ b/src/magnets/creator.py\n@@ -23,6 +23,7 @@\n             name=self.data['name'],\n             email=self.data['email'],\n             subscribe=True,\n+            tags=self.tags,\n         )()\n \n     def _create_log_entry(self):\n@@ -30,3 +31,7 @@\n             user=self.user,\n             campaign=self.campaign,\n         )\n+\n+    @property\n+    def tags(self):\n+        return [f'{self.campaign.slug}-lead-magnet']\ndiff --git a/src/shipping/shipments/course.py b/src/shipping/shipments/course.py\n--- a/src/shipping/shipments/course.py\n+++ b/src/shipping/shipments/course.py\n@@ -24,7 +24,7 @@\n             subscribe_to_mailchimp.delay(\n                 list_id=self.course.mailchimp_list_id,\n                 user_id=self.user.pk,\n-                tags=[self.course.slug],\n+                tags=[self.course.slug, f'{self.course.slug}-purchased'],\n             )\n \n     def invite_to_clickmeeting(self):\n", "issue": "\u041a\u0430\u0441\u0442\u043e\u043c\u043d\u044b\u0435 \u0442\u0435\u0433\u0438 \u0432 \u043c\u0435\u0439\u043b\u0447\u0438\u043c\u043f\u0435\n\u0427\u0442\u043e\u0431\u044b \u043c\u043e\u0436\u043d\u043e \u0431\u044b\u043b\u043e \u0432 \u043b\u0438\u0434-\u043c\u0430\u0433\u043d\u0438\u0442\u0435 \u0443\u043a\u0430\u0437\u0430\u0442\u044c \u0442\u0435\u0433\u0438, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043f\u0440\u043e\u0431\u0440\u0430\u0441\u044b\u0432\u0430\u044e\u0442\u0441\u044f \u0432 \u0430\u0443\u0434\u0438\u0442\u043e\u0440\u0438\u044e \u043c\u0435\u0439\u043b\u0447\u0438\u043c\u043f\u0430\n", "before_files": [{"content": "from magnets.models import EmailLeadMagnetCampaign, LeadCampaignLogEntry\nfrom users.creator import UserCreator\nfrom users.models import User\n\n\nclass LeadCreator:\n    def __init__(self, campaign: EmailLeadMagnetCampaign, email: str, name: str = None):\n        self.data = {\n            'name': name,\n            'email': email,\n        }\n\n        self.campaign = campaign\n\n    def __call__(self):\n        self.user = self._create_user()\n        self._create_log_entry()\n\n        self.campaign.execute(self.user)\n\n    def _create_user(self) -> User:\n        return UserCreator(\n            name=self.data['name'],\n            email=self.data['email'],\n            subscribe=True,\n        )()\n\n    def _create_log_entry(self):\n        LeadCampaignLogEntry.objects.create(\n            user=self.user,\n            campaign=self.campaign,\n        )\n", "path": "src/magnets/creator.py"}, {"content": "from typing import Optional\n\nfrom app.tasks import invite_to_clickmeeting, invite_to_zoomus, send_mail, subscribe_to_mailchimp\nfrom products.models import Course\nfrom shipping import factory\nfrom shipping.shipments.base import BaseShipment\n\n\n@factory.register(Course)\nclass CourseShipment(BaseShipment):\n    @property\n    def course(self):\n        return self.stuff_to_ship\n\n    def ship(self):\n        self.invite_to_clickmeeting()\n        self.invite_to_zoomus()\n        self.subscribe_to_mailchimp()\n\n        self.send_welcome_letter()\n\n    def subscribe_to_mailchimp(self):\n        if self.course.mailchimp_list_id is not None:\n            subscribe_to_mailchimp.delay(\n                list_id=self.course.mailchimp_list_id,\n                user_id=self.user.pk,\n                tags=[self.course.slug],\n            )\n\n    def invite_to_clickmeeting(self):\n        if self.course.clickmeeting_room_url is not None:\n            invite_to_clickmeeting.delay(\n                room_url=self.course.clickmeeting_room_url,\n                email=self.user.email,\n            )\n\n    def invite_to_zoomus(self):\n        if self.course.zoomus_webinar_id is not None and len(self.course.zoomus_webinar_id):\n            invite_to_zoomus.delay(\n                webinar_id=self.course.zoomus_webinar_id,\n                user_id=self.user.id,\n            )\n\n    def send_welcome_letter(self):\n        if self.welcome_letter_template_id is not None:\n            send_mail.delay(\n                to=self.user.email,\n                template_id=self.welcome_letter_template_id,\n                ctx=self.get_template_context(),\n                disable_antispam=True,\n            )\n\n    def get_template_context(self) -> dict:\n        return {\n            'name': self.course.name,\n            'slug': self.course.slug,\n            'name_genitive': self.course.name_genitive,\n            **self.get_gift_template_context(),\n        }\n\n    @property\n    def welcome_letter_template_id(self) -> Optional[str]:\n        \"\"\"Get special gift template letter id if order is a gift and it is present\"\"\"\n        template_id = self.course.welcome_letter_template_id\n\n        if self.order is not None and self.order.giver is not None:  # this is a gift\n            template_id = self.course.gift_welcome_letter_template_id or self.course.welcome_letter_template_id\n\n        if template_id is None or not len(template_id):  # fuck this null=True in CharFields\n            return None\n\n        return template_id\n", "path": "src/shipping/shipments/course.py"}]}