django-restit 4.2.79__py3-none-any.whl → 4.2.83__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
account/models/member.py CHANGED
@@ -224,11 +224,11 @@ class Member(User, RestModel, MetaDataModel):
224
224
 
225
225
  @property
226
226
  def force_single_session(self):
227
- return self.hasPermission("force_single_session")
227
+ return self.hasPermission("force_single_session", ignore_su=True)
228
228
 
229
229
  @property
230
230
  def email_disabled(self):
231
- return self.hasPermission("email_disabled")
231
+ return self.hasPermission("email_disabled", ignore_su=True)
232
232
 
233
233
  @property
234
234
  def has_totp(self):
account/models/notify.py CHANGED
@@ -130,6 +130,8 @@ class NotificationRecord(models.Model, RestModel):
130
130
 
131
131
  @classmethod
132
132
  def canSend(cls):
133
+ if not settings.get("THROTTLE_EMAILS", False):
134
+ return True
133
135
  max_emails_per_minute = settings.get("MAX_EMAILS_PER_MINUTE", 30)
134
136
  last_email = NotificationRecord.objects.filter(state=1).last()
135
137
  now = datetime.now()
@@ -206,7 +208,7 @@ class NotificationRecord(models.Model, RestModel):
206
208
 
207
209
  @classmethod
208
210
  def _notifyViaEmail(cls, member, subject, message, template, context,
209
- attachments, from_email=None):
211
+ attachments, from_email=settings.DEFAULT_FROM_EMAIL):
210
212
  # lets verify the db is working
211
213
  if template:
212
214
  if context is None:
@@ -215,6 +217,8 @@ class NotificationRecord(models.Model, RestModel):
215
217
  context["body"] = message
216
218
  context["unsubscribe_token"] = member.getUUID()
217
219
  message = inbox.utils.renderTemplate(template, context)
220
+ if from_email is None:
221
+ from_email = settings.DEFAULT_FROM_EMAIL
218
222
 
219
223
  nr = NotificationMemberRecord(member=member, to_addr=member.email)
220
224
  email_record = NotificationRecord(
@@ -0,0 +1,20 @@
1
+ # Generated by Django 4.2.11 on 2024-05-13 02:34
2
+
3
+ from django.db import migrations, models
4
+ import django.db.models.deletion
5
+
6
+
7
+ class Migration(migrations.Migration):
8
+
9
+ dependencies = [
10
+ ('sessionlog', '0001_initial'),
11
+ ('auditlog', '0001_initial'),
12
+ ]
13
+
14
+ operations = [
15
+ migrations.AlterField(
16
+ model_name='persistentlog',
17
+ name='session',
18
+ field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, to='sessionlog.sessionlog'),
19
+ ),
20
+ ]
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: django-restit
3
- Version: 4.2.79
3
+ Version: 4.2.83
4
4
  Summary: A Rest Framework for DJANGO
5
5
  License: MIT
6
6
  Author: Ian Starnes
@@ -28,9 +28,9 @@ account/models/device.py,sha256=TloXvvrx3khF3BeGFuVYn6DhXjOW0AMZb4F9Fl5nBII,5491
28
28
  account/models/feeds.py,sha256=vI7fG4ASY1M0Zjke24RdnfDcuWeATl_yR_25jPmT64g,2011
29
29
  account/models/group.py,sha256=iDD_oSgswKV_t_gXZuVK80MvICrZZqdANm2jtGtOFy8,21985
30
30
  account/models/legacy.py,sha256=zYdtv4LC0ooxPVqWM-uToPwV-lYWQLorSE6p6yn1xDw,2720
31
- account/models/member.py,sha256=v2cM7g5XoOQi_ZAlGcOcKn24zZCfAFokxUFIqNshDxc,52960
31
+ account/models/member.py,sha256=fzSVVAdbUa1knp1O4JTnYZFYRas7-zDZaOPjZAMCC1Q,52992
32
32
  account/models/membership.py,sha256=90EpAhOsGaqphDAkONP6j_qQ0OWSRaQsI8H7E7fgMkE,9249
33
- account/models/notify.py,sha256=Qzi8gLsVi8nDx8gpL4dyr0MPExYYGIDxZvHFUdCs7H4,15072
33
+ account/models/notify.py,sha256=iAq8tjyqouUelYgsMhWlchYmEAuCsKAyNIr5F8_xUeU,15258
34
34
  account/models/passkeys.py,sha256=TJxITUi4DT4_1tW2K7ZlOcRjJuMVl2NtKz7pKQU8-Tw,1516
35
35
  account/models/session.py,sha256=ELkWjB_2KXQvPtRPrvuGJpJsqrxCQX_4J53SbqGz_2U,3737
36
36
  account/models/settings.py,sha256=gOyRWBVd3BQpjfj_hJPtqX3H46ztyRAFxBrPbv11lQg,2137
@@ -65,6 +65,7 @@ auditlog/cloudwatch.py,sha256=R-B_ByVM3We26YnDoFYIQeWV31CUyS63QTojRAkfWa8,2805
65
65
  auditlog/decorators.py,sha256=ZoIv0fhZjxtMEV15NcKijW4xPF5UEScPna60zB3TxZo,6553
66
66
  auditlog/middleware.py,sha256=Q4bXg8rnm8y2fMnAsN6ha3Fz6TW8jIzLnvpu4H9SpWE,1537
67
67
  auditlog/migrations/0001_initial.py,sha256=X171gKQZIaTO9FGNG1yKTjGSZS0ZjZj5gvimF9-_kks,3309
68
+ auditlog/migrations/0002_alter_persistentlog_session.py,sha256=DkkcIobbHdbniKg5bOlRmiF-Nc4hX55Y6KuQySrCcJ8,541
68
69
  auditlog/migrations/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
69
70
  auditlog/models.py,sha256=skDAiuzR4chC-WNIaH2nm_VVcbnDD6ZtUxBwhk7UY8U,16517
70
71
  auditlog/periodic.py,sha256=AUhDeVsZtC47BJ-lklvYEegHoxAzj1RpIvRFSsM7g5E,363
@@ -79,6 +80,7 @@ inbox/migrations/0001_initial.py,sha256=P1OmbSHZGhj3wVBdFKWEzNrPdbyKzR9fFBXP8rhX
79
80
  inbox/migrations/0002_alter_message_cc.py,sha256=dsnDHCs1-dFZfSEWJmufBOs5gvNbI7u99kru6fVas0Y,380
80
81
  inbox/migrations/0003_attachment_content_type.py,sha256=dh_km90V6R3O0-N2oNTWhWLZZ96MylRgDY7Poua9CZ8,416
81
82
  inbox/migrations/0004_mailtemplate.py,sha256=yV51UdsRWmKC5Dy34-h2bXBeYeFtjoWQ7kOw7cuYCQo,1140
83
+ inbox/migrations/0005_alter_mailbox_state.py,sha256=trr-CCLupHQ7e-tjJK08LACdxhCApGMNBTOeWFcyXnI,393
82
84
  inbox/migrations/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
83
85
  inbox/models/__init__.py,sha256=yARvP31nhJGLjqP-U_ONi2OLjiTUFspdH0AlKynt4Y8,174
84
86
  inbox/models/bounce.py,sha256=3b_pCKH3gwb3NE8I1XlVI6JeoVmobZyKidsILH-jIRg,2881
@@ -106,18 +108,18 @@ incident/migrations/0011_ticket.py,sha256=Ml5E_Qi4Z0MD89fetoOFOL3rPlVQdjaaDCcFBf
106
108
  incident/migrations/0012_rule_match_by.py,sha256=PGclGnnc_8JEsJZ8znoXm-iAC6Y0i2WM6C2cmFgdKlA,372
107
109
  incident/migrations/0013_rulecheck_is_required.py,sha256=cL7tOj5XGPpKd2f5BojIKfNJeDB1IL-jGRU6-g-Co5o,387
108
110
  incident/migrations/0014_event_group_alter_rulecheck_index.py,sha256=v3gm5k0LVoas27qUDOt7el7YtK4yjFVLeEpuFUCoXaQ,724
111
+ incident/migrations/0015_rule_title_template_alter_incident_state.py,sha256=FPUDhFwqBC39EjeknRT7BPddEf6ExCjsXVb9LMqIn3U,687
109
112
  incident/migrations/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
110
113
  incident/models/__init__.py,sha256=NMphuhb0RTMf7Ov4QkNv7iv6_I8Wtr3xQ54yjX_a31M,209
111
- incident/models/event.py,sha256=i02lRMdBcjIty5w_wdZnYnW-RNXDANNfnsFouwlDYO8,7414
114
+ incident/models/event.py,sha256=Dw6fUi2tbLeA_ZRDcvGQNFkCkMGMBdtNeaLikXdAyE8,7769
112
115
  incident/models/incident.py,sha256=HPbi6J9qm7_-FMjnDUPV9NcbmP_60WU-IO9HJSpoLTY,19360
113
116
  incident/models/ossec.py,sha256=eUDRGawzuLWobKEVGKfdZisDnyjS_Hlxi0T_GCSLCCI,2252
114
- incident/models/rules.py,sha256=SMlDRw_r3fGv-vmRojRLmsklqRRxDcjrSLVBIz-gadA,6884
117
+ incident/models/rules.py,sha256=aRkJ0ZnTv87nAUC1sHVkPExfb3OJ8fgHQIhnCIpIbhQ,7001
115
118
  incident/models/ticket.py,sha256=S3kqGQpYLE6Y4M9IKu_60sgW-f592xNr8uufqHnvDoU,2302
116
119
  incident/parsers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
117
- incident/parsers/ossec.py,sha256=8SUma8wb2KmrcgACc6jESD_gXklCsMnKVyY7GrXYrtY,10812
120
+ incident/parsers/ossec.py,sha256=jyJmNBwnQS1tjZMwYhslnCpZviCHXnozv88BPT-ytCw,11592
118
121
  incident/periodic.py,sha256=eX1rQK6v65A9ugofTvJPSmAWei6C-3EYgzCMuGZ03jM,381
119
122
  incident/rpc.py,sha256=viJt873b8T8SiAq10EM57lF8g7ghyj3ymdkaXzh2Ass,8181
120
- incident/server.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
121
123
  incident/templates/email/incident_change.html,sha256=tQYphypwLukkVdwH0TB2Szz2VEJ7GnsfRS3_ZJ-MYeE,13895
122
124
  incident/templates/email/incident_msg.html,sha256=MZdKhTddUF2MpiH8Z3RTQEmW_ko1n3ajeZ11KLtiLlU,13780
123
125
  incident/templates/email/incident_new.html,sha256=W6nwFQROnyDfMlXub8s02ws4hGnJp16pfgp9xTm_aEc,15185
@@ -133,12 +135,12 @@ location/migrations/0004_remove_address_modified_by_address_group_and_more.py,sh
133
135
  location/migrations/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
134
136
  location/models/__init__.py,sha256=rZhldkoKmoJQXjBAK1IIQn7K_OOJvFtIGOGVl_szqbE,230
135
137
  location/models/address.py,sha256=wl0bToZ6VrJP923IIfzWqZY9xyKgla6A-uzj8jQFGRI,3149
136
- location/models/ip.py,sha256=ZaBFdW1tL1Q3bnS5gIY9SseiQ5xeeP_oyP1hp3czFeA,5984
138
+ location/models/ip.py,sha256=Bl-OlwEXGvKYvYSDBSsnQkeAi4ZTKs1mDt3ddc5rq80,6039
137
139
  location/models/legacy.py,sha256=8ROsUSZrjGQkUyXeJvoxPdKAWaKfUH-AL9TIeJb7krg,1994
138
140
  location/models/location.py,sha256=01dJPJecbp5orExsIGWOsBC_KkwFRIW0rGDIwyx1r0w,2316
139
141
  location/models/track.py,sha256=OdhRL1KVXlPcZkp4S6QpKc7Ctoth8VjwHs_dlZ8XHI4,1474
140
142
  location/providers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
141
- location/providers/iplookup/__init__.py,sha256=t7yiXnEopAN_NZ77k2oHAhfVCmWNDkiCKA8S41jbJv0,727
143
+ location/providers/iplookup/__init__.py,sha256=I0K0HZrluCsBZ1TlGGKnyavEDZ3mT-xfE7Dtq2k-F9k,790
142
144
  location/providers/iplookup/abstractapi.py,sha256=gY8eqpjEasZtiBC6nNu960ZGL96FVwNS2JoZuP1GBO4,2419
143
145
  location/providers/iplookup/extremeip.py,sha256=QNRGhwXXsOuJL2M-xiI2pFN_6LP2HkqSUpFosu5Q04M,1345
144
146
  location/providers/iplookup/geoplugin.py,sha256=RK_6McxHYlVVMVdJ2rCafw-kqMfzMm3g_tJjBwcKXYg,2121
@@ -473,6 +475,7 @@ telephony/phone_util.py,sha256=5NwSBnwBEC3EaeSeN42ggBiAQ00Ujvr6CepDjXLsCyw,5067
473
475
  telephony/rpc.py,sha256=PXPDFvgoXkCKlfMzIbt6lYZPay3fcveNj2X4Pjby7p4,3473
474
476
  wiki/__init__.py,sha256=AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs,1
475
477
  wiki/migrations/0001_initial.py,sha256=9jvUyjrbJrbDilRnwzQUPhPV8Xi_olEPBk_N0nycvM0,3606
478
+ wiki/migrations/0002_alter_pagemedia_entry.py,sha256=9CUnfvBmj0D4akCkux7HFuXgw9B9avE8V-iMCm5cjds,485
476
479
  wiki/migrations/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
477
480
  wiki/models/__init__.py,sha256=jE-9r_Hqpyo7ysKu9BschXOn5Zg34wUt894GwJpxA28,132
478
481
  wiki/models/faq.py,sha256=nvcEFerllQKT61kIYlasvZzRKwpXyfmQpiqkpHP1V1o,1745
@@ -503,7 +506,7 @@ ws4redis/servers/uwsgi.py,sha256=VyhoCI1DnVFqBiJYHoxqn5Idlf6uJPHvfBKgkjs34mo,172
503
506
  ws4redis/settings.py,sha256=K0yBiLUuY81iDM4Yr-k8hbvjn5VVHu5zQhmMK8Dtz0s,1536
504
507
  ws4redis/utf8validator.py,sha256=S0OlfjeGRP75aO6CzZsF4oTjRQAgR17OWE9rgZdMBZA,5122
505
508
  ws4redis/websocket.py,sha256=R0TUyPsoVRD7Y_oU7w2I6NL4fPwiz5Vl94-fUkZgLHA,14848
506
- django_restit-4.2.79.dist-info/LICENSE.md,sha256=VHN4hhEeVOoFjtG-5fVv4jesA4SWi0Z-KgOzzN6a1ps,1068
507
- django_restit-4.2.79.dist-info/METADATA,sha256=7Hya_J4qnHewCMwlz5m2Y2JLnN2b4TpVX2pVekbpjCw,7645
508
- django_restit-4.2.79.dist-info/WHEEL,sha256=sP946D7jFCHeNz5Iq4fL4Lu-PrWrFsgfLXbbkciIZwg,88
509
- django_restit-4.2.79.dist-info/RECORD,,
509
+ django_restit-4.2.83.dist-info/LICENSE.md,sha256=VHN4hhEeVOoFjtG-5fVv4jesA4SWi0Z-KgOzzN6a1ps,1068
510
+ django_restit-4.2.83.dist-info/METADATA,sha256=rbSXb9-b2DozTJTvyuPOVSB8x-7l1fWIhCqtR013RVg,7645
511
+ django_restit-4.2.83.dist-info/WHEEL,sha256=sP946D7jFCHeNz5Iq4fL4Lu-PrWrFsgfLXbbkciIZwg,88
512
+ django_restit-4.2.83.dist-info/RECORD,,
@@ -0,0 +1,18 @@
1
+ # Generated by Django 4.2.11 on 2024-05-13 02:34
2
+
3
+ from django.db import migrations, models
4
+
5
+
6
+ class Migration(migrations.Migration):
7
+
8
+ dependencies = [
9
+ ('inbox', '0004_mailtemplate'),
10
+ ]
11
+
12
+ operations = [
13
+ migrations.AlterField(
14
+ model_name='mailbox',
15
+ name='state',
16
+ field=models.IntegerField(db_index=True, default=1),
17
+ ),
18
+ ]
@@ -0,0 +1,23 @@
1
+ # Generated by Django 4.2.11 on 2024-05-13 02:34
2
+
3
+ from django.db import migrations, models
4
+
5
+
6
+ class Migration(migrations.Migration):
7
+
8
+ dependencies = [
9
+ ('incident', '0014_event_group_alter_rulecheck_index'),
10
+ ]
11
+
12
+ operations = [
13
+ migrations.AddField(
14
+ model_name='rule',
15
+ name='title_template',
16
+ field=models.CharField(default=None, max_length=200, null=True),
17
+ ),
18
+ migrations.AlterField(
19
+ model_name='incident',
20
+ name='state',
21
+ field=models.IntegerField(choices=[(0, 'new'), (1, 'opened'), (2, 'paused'), (3, 'ignored'), (4, 'resolved'), (5, 'pending')], default=0),
22
+ ),
23
+ ]
incident/models/event.py CHANGED
@@ -155,7 +155,7 @@ class Event(JSONMetaData, rm.RestModel):
155
155
  incident = None
156
156
  action_count = 0
157
157
  if hit_rule is not None:
158
- logger.error(f"RULE HIT: {hit_rule.name}")
158
+ # logger.error(f"RULE HIT: {hit_rule.name}")
159
159
  priority = hit_rule.priority
160
160
  if hit_rule.action == "ignore":
161
161
  self.save()
@@ -184,7 +184,13 @@ class Event(JSONMetaData, rm.RestModel):
184
184
  if hit_rule is not None and hit_rule.action_after != 0:
185
185
  incident.state = INCIDENT_STATE_PENDING
186
186
  # TODO possibly make this smarter?
187
- if self.category == "ossec":
187
+ if hit_rule and hit_rule.title_template and "{" in hit_rule.title_template:
188
+ try:
189
+ incident.description = hit_rule.title_template.format(event=self)
190
+ except Exception:
191
+ logger.exception(hit_rule.title_template)
192
+ incident.description = self.description
193
+ elif self.category == "ossec":
188
194
  incident.description = f"{self.hostname}: {self.description}"
189
195
  else:
190
196
  incident.description = self.description
incident/models/rules.py CHANGED
@@ -43,6 +43,7 @@ class Rule(models.Model, rm.RestModel):
43
43
  "created",
44
44
  "priority",
45
45
  "name",
46
+ "title_template",
46
47
  "category",
47
48
  "priority",
48
49
  "action",
@@ -63,6 +64,7 @@ class Rule(models.Model, rm.RestModel):
63
64
  modified = models.DateTimeField(auto_now=True)
64
65
 
65
66
  name = models.CharField(max_length=200)
67
+ title_template = models.CharField(max_length=200, default=None, null=True)
66
68
  # the group the rule gets assigned to when triggered
67
69
  group = models.ForeignKey("account.Group", on_delete=models.CASCADE, null=True, default=None)
68
70
  # category allows us to limit running rules to only those with a category
incident/parsers/ossec.py CHANGED
@@ -33,12 +33,21 @@ def parse_nginx_line(line):
33
33
  return None
34
34
 
35
35
 
36
- def removeNonAscii(input_str):
37
- """Remove all non-ASCII characters and escaped byte sequences from the input string."""
38
- # Remove escaped byte sequences
39
- cleaned_str = re.sub(r'\\x[0-9a-fA-F]{2}', '', input_str)
40
- # Remove non-ASCII characters
41
- return ''.join(char for char in cleaned_str if 32 <= ord(char) < 128)
36
+ def removeNonAscii(input_str, replacement=''):
37
+ """
38
+ Replace all non-ASCII characters and escaped byte sequences in the input string with a specified string.
39
+
40
+ Args:
41
+ input_str (str): The string to process.
42
+ replacement (str): The string to use as a replacement for non-ASCII characters and escaped byte sequences.
43
+
44
+ Returns:
45
+ str: The processed string with non-ASCII characters and byte sequences replaced.
46
+ """
47
+ # Replace escaped byte sequences with the replacement string
48
+ cleaned_str = re.sub(r'\\x[0-9a-fA-F]{2}', replacement, input_str)
49
+ # Replace non-ASCII characters with the replacement string
50
+ return ''.join(char if (32 <= ord(char) < 128 or char in '\n\r\t') else f"<r{str(ord(char))}>" for char in cleaned_str)
42
51
 
43
52
 
44
53
  def extractURL(text):
@@ -131,8 +140,12 @@ def parse_alert_metadata(alert):
131
140
  if match:
132
141
  return dict(filename=match.group(1), action="added")
133
142
  elif alert.rule_id == "5402":
134
- match = re.search(r'(?P<username>\w+) : PWD=(?P<pwd>\S+) ; USER=(?P<user>\w+) ; COMMAND=(?P<command>.+)', alert.text)
135
- return match.groupdict()
143
+ match = re.search(r'(?P<username>[\w-]+) : PWD=(?P<pwd>\S+) ; USER=(?P<user>\w+) ; COMMAND=(?P<command>.+)', alert.text)
144
+ if match:
145
+ return match.groupdict()
146
+ match = re.search(r'(?P<username>[\w-]+) : TTY=(?P<tty>\S+) ; PWD=(?P<pwd>\S+) ; USER=(?P<user>\w+) ; COMMAND=(?P<command>.+)', alert.text)
147
+ if match:
148
+ return match.groupdict()
136
149
  elif alert.rule_id in ["5501", "5502"]:
137
150
  match = re.search(r"session (?P<action>\S+) for user (?P<username>\S+)*", alert.text)
138
151
  if match:
@@ -164,6 +177,8 @@ def parse_alert_json(data):
164
177
  data = objict.fromJSON(removeNonAscii(data))
165
178
  for key in data:
166
179
  data[key] = data[key].strip()
180
+ if data.text:
181
+ data.text = removeNonAscii(data.text)
167
182
  return data
168
183
 
169
184
 
@@ -239,7 +254,8 @@ def update_by_rule(data, geoip=None):
239
254
  elif data.rule_id == "533":
240
255
  data.title = f"Network Open Port Change Detected on {data.hostname}"
241
256
  elif data.rule_id == "5402":
242
- data.title = f"Sudo(user: {data.user}) executed on {data.hostname}"
257
+ cmd = truncate_str(data.command, 50)
258
+ data.title = f"Sudo(user: {data.user}) executed '{cmd}' on {data.hostname}"
243
259
  elif data.rule_id in ["551", "554"] and data.filename:
244
260
  name = truncate_str(data.filename, 50)
245
261
  data.title = f"File {data.action.capitalize()} on {data.hostname}: {name}"
location/models/ip.py CHANGED
@@ -93,6 +93,8 @@ class GeoIP(models.Model, rm.RestModel):
93
93
  ip = ip.strip()
94
94
  if not geolocate.isIP(ip):
95
95
  ip = geolocate.dnsToIP(ip)
96
+ if ip is None:
97
+ return None
96
98
  subnet = ip[:ip.rfind(".")]
97
99
  gip = GeoIP.objects.filter(ip=ip).first()
98
100
  if gip is None:
@@ -32,4 +32,8 @@ def isIP(ip):
32
32
 
33
33
 
34
34
  def dnsToIP(name):
35
- return socket.gethostbyname(name)
35
+ try:
36
+ return socket.gethostbyname(name)
37
+ except Exception:
38
+ pass
39
+ return None
@@ -0,0 +1,19 @@
1
+ # Generated by Django 4.2.11 on 2024-05-13 02:34
2
+
3
+ from django.db import migrations, models
4
+ import django.db.models.deletion
5
+
6
+
7
+ class Migration(migrations.Migration):
8
+
9
+ dependencies = [
10
+ ('wiki', '0001_initial'),
11
+ ]
12
+
13
+ operations = [
14
+ migrations.AlterField(
15
+ model_name='pagemedia',
16
+ name='entry',
17
+ field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='media_library', to='wiki.page'),
18
+ ),
19
+ ]
incident/server.py DELETED
File without changes