Administrative Massenoperationen

Im Folgenden finden Sie eine Sammlung von Massenoperationen, die über die Befehlszeile eingeleitet werden können. Sie benötigen SSH-Zugriff. Wenn Sie ein gehosteter Kunde sind, müssen Sie sich an das Discourse-Team wenden, um diese Befehle ausführen zu lassen.

:warning: Bevor Sie mit der Konsole arbeiten, ist es äußerst wichtig, dass Sie über ein aktuelles Backup verfügen. Fehler können immer passieren!

Das erste, was zu tun ist, besteht darin, den Container Ihrer Site zu betreten:

cd /var/discourse
./launcher enter app

Zusätzliche Anleitungen:

Status von Themen ändern


Führen Sie vor dem Ausführen der folgenden Befehle rails c aus, um die Konsole zu starten.

  • Alle Themen innerhalb einer Kategorie aus der Liste entfernen (schließt Post-Aktionen aus)

    Sie können visible durch closed oder archived ersetzen und die true/false-Werte nach Bedarf anpassen

    cat_id = Category.find_by_slug('admins').id
    Topic.where(category_id: cat_id, visible: true).update_all(visible: false)
    
  • Alle Themen innerhalb einer Kategorie aus der Liste entfernen (schließt Post-Aktionen ein)

    cat_id = Category.find_by_slug("admins").id
    Topic.where(category_id: cat_id, visible: true).find_each do |topic| 
      topic.update_status('visible', false, Discourse.system_user)
    end
    
  • Alle Themen schließen, die vor einem bestimmten Datum erstellt wurden (schließt Post-Aktionen ein)

    Topic.where(closed: false).where("created_at < '2015-01-01'").find_each do |topic| 
      topic.update_status('closed', true, Discourse.system_user)
    end
    

Themen verschieben


Verschieben Sie eine Sammlung von Themen von einer Kategorie in eine andere

rails c
topic_ids = [12,16,29]
cat_to = Category.find_by_slug('faq')
Topic.where(id: topic_ids).update_all(category_id: cat_to.id)
Category.update_stats

Benutzer

Teilmenge von Benutzern löschen


Benutzer löschen, die niemals gepostet haben und seit einem bestimmten Datum nicht mehr besucht haben

rails c
User.joins(:user_stat).where("user_stats.post_count = 0 AND previous_visit_at <= '2016-05-20'::timestamp").destroy_all

Eine Reihe von Benutzern basierend auf Kriterien sperren


Festlegen, wer als Sperrende der Benutzer protokolliert wird

rails c
logger = StaffActionLogger.new(User.find_by(username_lower: "tshenry"))

Einen Sperrezeitraum und einen Grund erstellen

suspend_till = DateTime.new(2057,12,31)
reason = 'Completed Course'

In diesem Beispiel sind unsere Benutzerkriterien die Gruppenmitgliedschaft.

target_group = Group.find_by_name("summer_students")
users = User.joins(:group_users).where(group_users: {group_id: target_group.id})

Jeden Benutzer basierend auf den oben festgelegten Werten sperren:

users.find_each do |u|
  u.suspended_till = suspend_till
  u.suspended_at = DateTime.now
  u.save!

  logger.log_user_suspend(u,reason)
  putc '.'
end

Sperrgründe für Benutzer aktualisieren


Vielleicht haben Sie Benutzer gesperrt, die einen Kurs abgeschlossen haben (siehe Beispiel oben), und möchten nun das Jahr des Kurses hinzufügen, da Sie mehrere Jahre unterrichtet haben.

UserHistory.where(action: 10, details: "Completed Course").update_all(details: "Completed 2018 Course")

Sperren von Benutzern aufheben


Wenn Sie Benutzer massenhaft entsperren müssen, beispielsweise weil sie Teil einer Kohorte des Vorjahres waren und in diesem Jahr zurückkehren, können Sie dies wie unten gezeigt tun. Im Beispiel suchen wir Benutzer nach ihrer Benutzer-ID.

user_list = [1, 3, 5, 7, 11]
users = User.where("id in (?)", user_list)

users.each do |user|
    user.suspended_till = nil
    user.suspended_at = nil
    user.save!
    StaffActionLogger.new(User.find(-1)).log_user_unsuspend(user)

    DiscourseEvent.trigger(:user_unsuspended, user: user)
end

Export/Import

Alle Site-Einstellungen exportieren/importieren


Um einfach alle Einstellungen auszugeben, die auf Ihrer Site geändert wurden, führen Sie Folgendes aus:

rake site_settings:export

Wenn Sie die Einstellungen in eine Datei exportieren möchten:

rake site_settings:export > saved_settings.yml

Wenn Sie Einstellungen aus einer Datei importieren möchten:

rake site_settings:import < saved_settings.yml

Kategorien exportieren/importieren


Es gibt zwei Optionen für den Export und eine Methode für den Import.

Eine Reihe vollständiger Kategorien exportieren

Zuerst eine Liste Ihrer Kategorie-IDs abrufen:

rake categories:list

Dann die Kategorie-IDs im Export-Rake-Auftrag durch Leerzeichen trennen. Zum Beispiel:

rake export:categories["12 6"]

Die Kategorienstruktur Ihrer Site exportieren

Dies entspricht im Wesentlichen dem Kopieren des „Gerüsts“ Ihrer Discourse-Site. Es enthält jede Kategorie sowie alle Gruppen, die mit bestehenden Kategorienberechtigungen verknüpft sind. Es enthält keine Themen:

rake export:category_structure

Wenn Sie die Kategorienstruktur zusammen mit allen Gruppen, die mit den Kategorienberechtigungen verknüpft sind, und allen Mitgliedern dieser Gruppen möchten:

rake export:category_structure[true]

Eine Kategoriendatei importieren

Verwenden Sie den Namen der exportierten Datei wie im folgenden Beispiel:

rake import:file["category-export-2019-05-16-052430.json"]

Gruppen exportieren/importieren


Alle Benutzergruppen exportieren

rake export:groups

Alle Benutzergruppen einschließlich Benutzer exportieren

rake export:groups[true]

Eine Gruppendatei importieren
Verwenden Sie den Namen der exportierten Datei wie im folgenden Beispiel:

rake import:file["group-export-2019-05-16-052430.json"]

Berechtigungen für mehrere Kategorien festlegen


:warning: Beachten Sie, dass dies alle bestehenden Zugriffsbeschränkungen entfernt, die Sie für die betroffenen Kategorien eingerichtet haben. Stellen Sie sicher, dass Sie alle relevanten Berechtigungen einschließen.

  1. Eine Liste der Kategorien zusammen mit ihren IDs abrufen

    rails c
    Category.all.pluck("name", "id")
    
  2. Ein Array mit den Kategorie-IDs erstellen, die Sie adressieren möchten.

    category_ids = [6,7,8,10]
    
  3. Die Berechtigungen ändern. Die Funktion set_permissions kann die folgenden Parameter verwenden: :full, :create_post, :readonly

    • Eine einzelne Berechtigung. Zum Beispiel eine Reihe von Kategorien nur für Mitarbeiter zugänglich machen:

      Category.where(id: category_ids).find_each do |category| 
       category.set_permissions(:staff => :full)
       category.save!
      end
      
    • Mehrere Berechtigungen. Zum Beispiel eine Reihe von Kategorien für normale Benutzer schreibgeschützt machen:

      Category.where(id: category_ids).find_each do |category| 
        category.set_permissions(:everyone => :readonly, :staff => :full)
        category.save!
      end
      
    • Benutzergruppenberechtigungen. Zum Beispiel einer Gruppe volle Berechtigungen und einer anderen Gruppe schreibgeschützten Zugriff für eine Reihe von Kategorien gewähren:

      artists_group = Group.find_by_name("artists")
      buyers_group = Group.find_by_name("buyers")
      Category.where(id: category_ids).find_each do |category| 
        category.set_permissions(artists_group.id => :full, buyers_group.id => :readonly)
        category.save!
      end
      

Alle Themen basierend auf einem Schlüsselwort massenhaft taggen

Das folgende Skript ermöglicht es Ihnen, Themen basierend auf dem Vorhandensein eines Schlüsselworts im Titel des Themas oder in seinen Beiträgen zu taggen. Beginnen Sie mit der Erstellung eines Arrays von Schlüsselwörtern:

rails c
keywords = ['apples','oranges']

Als Nächstes müssen wir eine Methode definieren:

def tag_by_keyword(word, tag_name)
  tag = Tag.find_by_name(tag_name) || Tag.create(name: tag_name)
  keyword_topics = Topic.joins(:posts).where("topics.title ~* :keyword or posts.raw ~* :keyword", keyword: "\\y#{word}\\y").distinct

  keyword_topics.each do |topic|
    if topic.tags.exclude?(tag)
      topic.tags << tag
    end
  end
end

Und schließlich jedes Schlüsselwort durch die Methode laufen lassen. Das Folgende wird jedes relevante Thema mit einem Tag namens „fruit“ taggen:

keywords.each { |word| tag_by_keyword(word, 'fruit') }

Alle Themen innerhalb einer Kategorie massenhaft taggen


Vorlage: rake tags:bulk_tag_category["<tag>|<tag>",<category_id>]
Dies wäre besonders nützlich, wenn man versucht, eine Kategorie in ein Tag umzuwandeln.

Verwenden Sie zunächst den folgenden Rake-Auftrag, um die relevante Kategorie-ID zu finden.

rake categories:list

Alle Themen der angegebenen Kategorie taggen. In diesem Beispiel würden Sie alle Themen in der Kategorie mit der ID 6 mit dem Tag „support“ taggen. :warning: Dies entfernt alle anderen Tags von jedem Thema.

rake tags:bulk_tag_category["support",6]

Alle Themen der angegebenen Kategorie anhängen. In diesem Beispiel würden Sie das Tag „support“ zu allen Themen in der Kategorie mit der ID 6 hinzufügen, während bestehende Tags erhalten bleiben.

rake tags:bulk_tag_category["support",6,true]

Alle Themen mit einem bestimmten Tag in eine einzelne Kategorie verschieben

Wenn Sie versuchen, Ihre Discourse-Site umzustrukturieren, stellen Sie möglicherweise fest, dass Sie eine Sammlung von Themen verschieben möchten, ohne Benachrichtigungen auszulösen. Eine Möglichkeit, dies zu tun, besteht darin, ein temporäres Tag zu erstellen, das Tag auf die entsprechenden Themen anzuwenden, die Themen unter Verwendung des unten stehenden Codes in eine bestimmte Kategorie zu verschieben und schließlich das temporäre Tag zu löschen.

Das Tag abrufen.

rails c
tag = Tag.find_by_name("tutorial")

Zielkategorie abrufen.

  • Für reguläre Kategorien:
cat_to = Category.find_by_slug('guides')
  • Für Unterkategorien:
cat_to = Category.find_by_slug('child-slug','parent-slug')

Die getaggten Themen in die Zielkategorie verschieben.

Topic.joins(:topic_tags).where("topic_tags.tag_id = ?", tag.id).update_all(category_id: cat_to.id)

Die Themenanzahlen der betroffenen Kategorien aktualisieren.

Category.update_stats
CategoryTagStat.update_topic_counts

Alle Themen von einer Kategorie in eine andere verschieben


Die Kategorie-IDs mit dem folgenden Rake-Auftrag finden:

rake categories:list

Der erste Wert sollte die Startkategorie-ID sein. Der zweite Wert sollte die Zielkategorie-ID sein.

rake categories:move_topics[15,6]
Rails Console Script
cat_from_id = XX # Kategorie, aus der Themen verschoben werden sollen
cat_to_id = XX  # Kategorie, in die Themen verschoben werden sollen
Topic.where(category_id: cat_from_id).update_all(category_id: cat_to_id)
Category.update_stats
CategoryTagStat.update_topic_counts

Eigentümer aller Themen in Kategorien ändern


Die Kategorie-IDs mit dem folgenden Rake-Auftrag finden:

rake categories:list

Den neuen Eigentümer und die zu bearbeitenden Kategorien angeben. Die Kategorien sollten ein Array von Kategorie-IDs sein, im Beispiel die Kategorien 1, 2 und 3:

rails c
user = User.find_by(username_lower: "lowercase-username")
categories = [1, 2, 3]

Alle Themen-IDs für die angegebenen Kategorien abrufen und den Eigentümer des ersten Beitrags in allen übereinstimmenden Themen ändern.

topics = Topic.where(category_id: categories).pluck(:id)

topics.each do |topic|
  PostOwnerChanger.new(
    post_ids: Post.where(topic_id: topic).where(post_number: 1).pluck(:id),
    topic_id: topic,
    new_owner: user,
    acting_user: Discourse.system_user,
    skip_revision: true
  ).change_owner!
end

Allen Gruppenmitgliedern ein Abzeichen erteilen


Allen Benutzern, die einer bestimmten Gruppe angehören, ein Abzeichen erteilen. Der erste Wert ist die Gruppen-ID und der zweite ist die Abzeichen-ID.

rails c
Group.find_by_name("event_participants").id
Badge.find_by_name("event_badge").id
exit
rake groups:grant_badge[42,102]

:warning: Beachten Sie, dass der oben genannte Rake-Auftrag nur ein Abzeichen erteilt; er wird ein zuvor erteiltes Abzeichen nicht widerrufen, wenn ein Benutzer nicht mehr Teil der angegebenen Gruppe ist. Wenn Sie massenhaft Abzeichen für alle Benutzer widerrufen müssen, die nicht mehr Teil einer Gruppe sind, können Sie Folgendes ausführen:

rails c

badge_id = Badge.find_by_name("Some Group Member").id

group = Group.find_by_name("Some_Group")

group_user_id = group.users.pluck("id")

userBadge = UserBadge.where.not(user_id: group_user_id).where(badge_id: badge_id)

userBadge.each do |ub|
  BadgeGranter.revoke(ub, revoked_by: Discourse.system_user)
end

exit

Sicherstellen, dass alle Benutzer auf ihrem automatischen Vertrauenslevel sind


Angenommen, Sie haben das Standardvertrauenslevel für neue oder eingeladene Benutzer auf einen Wert gesetzt, der nicht ganz so funktioniert, wie Sie es erwartet haben (z. B. TL4). Jetzt möchten Sie es so ändern, dass Ihre Benutzer auf dem Vertrauenslevel sind, das sie aufgrund ihrer aktuellen Statistiken automatisch hätten. Die folgenden Befehle stellen sicher, dass alle Benutzer auf dem Vertrauenslevel sind, das sie gemäß Understanding Discourse Trust Levels haben sollten. Hinweis: Benutzer mit gesperrten Vertrauenslevels werden nicht betroffen sein.

Stellen Sie sicher, dass alle Benutzer auf das richtige Vertrauenslevel gesetzt sind:

rails c
User.all.find_each do |user|
  Promotion.recalculate(user)
end

Die Gruppenstatistiken aktualisieren, um die Änderungen widerzuspiegeln:

Group.ensure_consistency!

Skripte zur Themenwartung

Die folgenden Ruby-Skripte zeigen, wie automatisierte Wartung an Themen basierend auf Aktivitätsdaten und anderen Kriterien durchgeführt wird. Diese Skripte kombinieren SQL-Abfragen, um Themen zu identifizieren, mit Ruby-Code, um Aktionen an ihnen durchzuführen, und müssen über die Rails-Konsole für Ihre Site ausgeführt werden.

Jedes Skript folgt einem ähnlichen Muster:

  1. Eine SQL-Abfrage, die relevante Themen identifiziert
  2. Ruby-Code, der jedes Thema verarbeitet und die gewünschten Aktionen anwendet
  3. Grundlegende Fehlerbehandlung und Protokollierung

Diese Skripte können angepasst werden durch:

  • Anpassung der Zeiträume (z. B. „6 MONTH“, „1 YEAR“, „2 YEAR“)
  • Ändern der Kategorieauswahlen, um Ihrer Forumstruktur zu entsprechen
  • Ändern der durchzuführenden Aktionen (schließen, aus der Liste entfernen oder verschieben)
  • Hinzufügen zusätzlicher Bedingungen wie Beitragsanzahl oder Ansichtsschwellenwerte

Inaktive Themen schließen, aus der Liste entfernen und verschieben

Dieses Skript identifiziert Themen, die die folgenden Kriterien erfüllen:

  • In einer bestimmten Kategorie
  • Offen
  • Ungelöst (unter Verwendung des Discourse Solved Plugins)
  • Keine kürzliche Aktivität innerhalb eines bestimmten Zeitraums

Führt dann mehrere Aktionen aus:

  • Schließt sie,
  • Entfernt sie aus der Liste und
  • Verschiebt sie in eine ausgewiesene Kategorie für veraltete Inhalte
SQL Query
WITH topic_list AS (
    SELECT ua.target_topic_id, MAX(ua.created_at) "created_at"  
    FROM user_actions ua
    INNER JOIN topics t ON t.id = ua.target_topic_id
    INNER JOIN categories c ON c.id = t.category_id
    LEFT JOIN discourse_solved_solved_topics solved ON solved.topic_id = t.id
    WHERE t.closed = false
        AND t.category_id = [CATEGORY_ID]
        AND solved.topic_id IS NULL
        AND t.deleted_at IS NULL
    GROUP BY ua.target_topic_id
    HAVING MAX(ua.created_at) <= (CURRENT_DATE - (INTERVAL '[TIME_PERIOD]'))
    ORDER BY "created_at" DESC
)
    
SELECT '' AS total, target_topic_id AS topic_id, created_at 
FROM topic_list
UNION
SELECT ''||COUNT(*), 0, CURRENT_DATE
FROM topic_list
ORDER BY created_at DESC
Combined SQL + Script
sql = "WITH topic_list AS (
    SELECT ua.target_topic_id, MAX(ua.created_at) \"created_at\"  
    FROM user_actions ua
    INNER JOIN topics t ON t.id = ua.target_topic_id
    INNER JOIN categories c ON c.id = t.category_id
    LEFT JOIN discourse_solved_solved_topics solved ON solved.topic_id = t.id
    WHERE t.closed = false
        AND t.category_id = [CATEGORY_ID]
        AND solved.topic_id IS NULL
        AND t.deleted_at IS NULL
    GROUP BY ua.target_topic_id
    HAVING MAX(ua.created_at) <= (CURRENT_DATE - (INTERVAL '[TIME_PERIOD]'))
    ORDER BY \"created_at\" DESC
)
    
SELECT '' AS total, target_topic_id AS topic_id, created_at 
FROM topic_list
UNION
SELECT ''||COUNT(*), 0, CURRENT_DATE
FROM topic_list
ORDER BY created_at DESC"

results = ActiveRecord::Base.connection.execute(sql)
user = Discourse.system_user
destination_category = Category.find([DESTINATION_CATEGORY_ID])

puts "Found #{results.count} topics to process"

results.each do |row|
    begin
    topic = Topic.find(row["topic_id"])
    
    # 1. In Zielkategorie verschieben
    topic.update!(category_id: destination_category.id)
    puts "#{topic.id} moved to destination category"
    
    # 2. Thema schließen
    topic.update_status('closed', true, user, until: nil)
    puts "#{topic.id} is closed"
    
    # 3. Thema aus der Liste entfernen
    topic.update_status('visible', false, user, until: nil)
    puts "#{topic.id} is unlisted"

    # Fehlerbehandlung
    rescue => e
      puts "Error processing topic #{row["topic_id"]}: #{e.message}"
    end
end

puts "Process completed"

Gelöste Themen mit keiner kürzlichen Aktivität schließen

Dieses Skript schließt gelöste Themen, die für einen definierten Zeitraum inaktiv waren. Dies kann helfen, Ihr Forum aufgeräumt zu halten, während wertvolle gelöste Themen erhalten bleiben.

Dieses Skript identifiziert Themen, die die folgenden Kriterien erfüllen:

  • In einer bestimmten Kategorie
  • Offen
  • Gelöst (unter Verwendung des Discourse Solved Plugins)
  • Keine kürzliche Aktivität innerhalb eines bestimmten Zeitraums
SQL Query
WITH topic_list AS (
    SELECT ua.target_topic_id, MAX(ua.created_at) "created_at"  
    FROM user_actions ua
    INNER JOIN topics t ON t.id = ua.target_topic_id
    INNER JOIN categories c ON c.id = t.category_id
    INNER JOIN discourse_solved_solved_topics solved ON solved.topic_id = t.id
    WHERE t.closed = false
        AND t.category_id IN ([CATEGORY_IDS])
        AND t.deleted_at IS NULL
    GROUP BY ua.target_topic_id
    HAVING MAX(ua.created_at) <= (CURRENT_DATE - (INTERVAL '[TIME_PERIOD]'))
    ORDER BY "created_at" DESC
)
    
SELECT '' AS total, target_topic_id AS topic_id, created_at 
FROM topic_list
UNION
SELECT ''||COUNT(*), 0, CURRENT_DATE
FROM topic_list
ORDER BY created_at DESC
Combined SQL + Script
sql = "WITH topic_list AS (
    SELECT ua.target_topic_id, MAX(ua.created_at) \"created_at\"  
    FROM user_actions ua
    INNER JOIN topics t ON t.id = ua.target_topic_id
    INNER JOIN categories c ON c.id = t.category_id
    INNER JOIN discourse_solved_solved_topics solved ON solved.topic_id = t.id
    WHERE t.closed = false
        AND t.category_id IN ([CATEGORY_IDS])
        AND t.deleted_at IS NULL
    GROUP BY ua.target_topic_id
    HAVING MAX(ua.created_at) <= (CURRENT_DATE - (INTERVAL '[TIME_PERIOD]'))
    ORDER BY \"created_at\" DESC
)
    
SELECT '' AS total, target_topic_id AS topic_id, created_at 
FROM topic_list
UNION
SELECT ''||COUNT(*), 0, CURRENT_DATE
FROM topic_list
ORDER BY created_at DESC"

results = ActiveRecord::Base.connection.execute(sql)
user = Discourse.system_user

puts "Found #{results.count} topics to process"

results.each do |row|
    begin
    topic = Topic.find(row["topic_id"])
     
    # Thema schließen
    topic.update_status('closed', true, user, until: nil)
    puts "#{topic.id} is closed"

    # Fehlerbehandlung
    rescue => e
      puts "Error processing topic #{row["topic_id"]}: #{e.message}"
    end
end

puts "Process completed"

Previously geschlossene Themen archivieren

Dieses Skript identifiziert Themen, die vor einem bestimmten Datum geschlossen wurden, und verschiebt sie in eine Archivkategorie, während sie aus der Liste entfernt werden.

SQL Query
WITH topic_list AS (
    SELECT 
        t.id AS topic_id, 
        tt.execute_at AS closed_at
    FROM topics t
    INNER JOIN categories c ON c.id = t.category_id
    LEFT JOIN topic_timers tt ON tt.topic_id = t.id AND tt.status_type IN (1, 8)
    WHERE t.closed = true
        AND t.category_id IN ([CATEGORY_IDS])
        AND t.deleted_at IS NULL
        AND tt.execute_at IS NOT NULL
        AND tt.execute_at <= (CURRENT_DATE - INTERVAL '[TIME_PERIOD]')
    ORDER BY tt.execute_at DESC
)
    
SELECT '' AS total, topic_id, closed_at 
FROM topic_list
UNION
SELECT ''||COUNT(*), 0, CURRENT_DATE
FROM topic_list
ORDER BY closed_at DESC
Combined SQL + Script
sql = "WITH topic_list AS (
    SELECT 
        t.id AS topic_id, 
        tt.execute_at AS closed_at
    FROM topics t
    INNER JOIN categories c ON c.id = t.category_id
    LEFT JOIN topic_timers tt ON tt.topic_id = t.id AND tt.status_type IN (1, 8)
    WHERE t.closed = true
        AND t.category_id IN ([CATEGORY_IDS])
        AND t.deleted_at IS NULL
        AND tt.execute_at IS NOT NULL
        AND tt.execute_at <= (CURRENT_DATE - INTERVAL '[TIME_PERIOD]')
    ORDER BY tt.execute_at DESC
)
    
SELECT '' AS total, topic_id, closed_at 
FROM topic_list
UNION
SELECT ''||COUNT(*), 0, CURRENT_DATE
FROM topic_list
ORDER BY closed_at DESC"

results = ActiveRecord::Base.connection.execute(sql)
user = Discourse.system_user
archive_category = Category.find([ARCHIVE_CATEGORY_ID])

puts "Found #{results.count} topics to process"

results.each do |row|
    begin
    topic = Topic.find(row["topic_id"])
    
    # 1. In Archivkategorie verschieben
    topic.update!(category_id: archive_category.id)
    puts "#{topic.id} moved to archive category"
    
    # 2. Thema aus der Liste entfernen
    topic.update_status('visible', false, user, until: nil)
    puts "#{topic.id} is unlisted"

    # Fehlerbehandlung
    rescue => e
      puts "Error processing topic #{row["topic_id"]}: #{e.message}"
    end
end

puts "Process completed"

Destruktive Rake-Aufträge


Ganze Kategorien löschen

Das Folgende ermöglicht es Ihnen, mehrere Kategorien zusammen mit allen Unterkategorien und Themen, die zu diesen Kategorien gehören, zu zerstören.

Eine Liste der Kategorie-IDs ausgeben

rake categories:list

Eine Reihe von Kategorien basierend auf ihrer ID zerstören

rake destroy:categories[10,11,12,18,30]

Alle Themen in einer Kategorie löschen

Alle persönlichen Nachrichten entfernen

rake destroy:private_messages

Alle Gruppen zerstören

rake destroy:groups

Alle Nicht-Admin-Benutzer zerstören

rake destroy:users

Site-Statistiken zerstören

rake destroy:stats

Alle Benutzer außer Mitarbeitern anonymisieren

rake users:anonymize_all

Eine Reihe von Beiträgen dauerhaft löschen

Der folgende Rake-Auftrag wird eine Liste von Beiträgen basierend auf ihrer ID hart löschen. Wenn ein Beitrag der erste Beitrag in einem Thema ist, werden alle Beiträge in diesem Thema hart gelöscht. Bevor Sie die Aufgabe erfolgreich ausführen können, muss die Site-Einstellung can_permanently_delete aktiviert sein.

:warning: Sobald ein Beitrag durch diese Aufgabe gelöscht wurde, existiert er nicht mehr in der Datenbank und kann nicht wiederhergestellt werden.

Es gibt zwei mögliche Ansätze:

  • Option 1 – Eine durch Kommas getrennte Liste von Beitrags-IDs als Argument übergeben

    rake destroy:posts[4,8,15,16,23,42]
    
  • Option 2 – Eine Textdatei mit einer durch Kommas getrennten Liste von Beitrags-IDs angeben (ideal für große Mengen von Beiträgen).

    cat post_ids.txt | rake destroy:posts
    

Ich habe versucht, die nützlichsten Rake-Aufträge in diesem Thema aufzunehmen, aber es gibt viele andere, die mit Discourse ausgeliefert werden. Wenn Sie eine umfassende Liste sehen möchten, können Sie Folgendes verwenden:

Alle Aufgaben mit Beschreibungen

rake --tasks

Alle Aufgaben, einschließlich derer, die keine Beschreibungen haben

rake -AT
70 „Gefällt mir“
Performing bulk actions as a moderator
Ruby on rails console command
Backup only Site Settings
How to move all topics of 1 category to new tag
Error Message when editing large number of topics
Delete/Remove All Tags in Bulk
How To Apply signature to every user?
How can I directly edit Discourse database from a GUI?
Bulk open closed topics
Suggest favorite YouTube tutorials for Discourse Admins and Moderators
Error Message when editing large number of topics
How to truncate bounced email log
Is there a way to grant badge to a group of user?
What makes a successful volunteer Discourse sysadmin?
How to extend time of all suspended users by one command?
Is there a bulk administrative command to aprove users?
DiscoTOC mobile view does not work with Docs
How might we better structure #howto?
Moving from sub-categories to tags?
Moving from sub-categories to tags?
Automatic Admin settings backups
How to get rid of thousands of topics that have no value?
Setting the api key via console
Bulk Action on Users
Mass-edit (or review) category parameters
How to activate and unstage accounts for imported users
Moving a group to TL3
Bulk Category Creation via CSV
Adding bulk categories
Can I/how to convert a tag to a category?
Rake post without confirmation
A few questions about batch moving or deleting topics
Restoring Deleted Messages?
Bulk Ownership Change of First Posts by Tag – Script Review and Suggestions
What makes a successful volunteer Discourse sysadmin?
Understanding and using badges
How to recalculate all trust_levels?
Adding many categories
How to Delete Active Users whose Readtime is less or not logged in since long or not visited since long?
How to Reset Site Statistics or Recalculate?
A community template emphasizing place and intent
Docker attach gives empty new line
Change notification settings for all users per topic
Why is there a category that I can't modify
How to sort topics in Latest by creation date?
"Period" in tag
Bulk move many topics from one category to another
Can I disable choosing a default homepage in users' Interface settings?
Bulk delete all topics in a category
Update all users email watchlist with a (newly created) category
How to change owner of invite links?
Trust level names in spanish
Admin guide to tags in Discourse
Assign users a random digest time?
How to change language of all users?
Requesting help demoting users with invalid email addresses
Rake import category doesn't respect parent category
Is there a non-query way to remove a bulk of users from groups?
Set up file and image uploads to S3
Hide Muted Categories
Modify trust level for all users
Create user without sending invite
Removing specific staff action logs using the console
Is it possible to make database changes using postgres rather than rake?
Applying Watched Words to existing posts
Bulk changing subcategories doesn't select all topics?
How to update and unlock all groups?
CLI Command for Deleting Category
Apply preferences settings for all normal users globally
Switch all users to TL2
How to add multiple tags up front
Creating and configuring custom user fields
How to delete EVERYTHING from my forum and just leave the users?
Back up only the settings
Bulk mark messages and posters as spam
Bulk mark messages and posters as spam
Staff category permission change
Convert all existing topics in category to wikis
Migrate a phpBB3 forum to Discourse
Manage multiple Discourse instances from one place only
Merge categories
Bulk Importing Groups Fails
Automatically replacing some tags with categories on existing forum
Mass closing topics
User monetization with group access?
A way to trigger auto-tagging across all topics for a new watched word
Convert a category to private and add users to a specific group with access
How to mass remove PMs?
RSS Polling
Mass Revoking Badges
How to turn off forum except for staff
Cannot delete tag with 2k topics
Is it possible to limit TL0 to posting in one category?
Mass close existing topics older than x?
Mass close existing topics older than x?
How to import category with category permissions?
Bulk open closed topics
Get Error Oops The software powering this discussion forum encountered an unexpected problem after upgrade
How do I back up only forum configuration information?
Question about category populating with certain tags
How extensible can I make my installation in terms of sub domains and restricting membership to them?
Automatically re-categorize topics from an imported forum by targeting keywords in titles?
How to clear all historical statistics from dashboard
Create a category that's private to one group, but open to other groups
自定义表情符号能否支持批量删除?
Unable to Bulk Suspend/Deactivate Users in Rails Console on Discourse 3.5.0.beta5-dev
How to Disable ALL User-to-User DMs/Chat without breaking Other Features?
Move Some topics to New Instance
Structure and duplication of category contents intra discourse and between discourse sites
Is there a way to convert categories into tags?
Structuring an active support community migrating from Facebook
How to delete thousands of Personal Messages?
Multilingual Plugin :globe_with_meridians:
Moving from sub-categories to tags?
How to change topic date after import
Emoji Fluff
Export/import theme components in bulk?
Need To Reopen All Topics!
How to bulk delete old whispers
Add a tag to all topics in a category
How to Create a Script to "Bulk Remove" from a Group?
How to delete all warnings?
Marking multiple account as Suspended account
How can I directly edit Discourse database from a GUI?
Are conditions to get new Trust level cumulative?
Bulk Remove Members from a Group
Can't reverse silencing a category for a group
Assigning mod status to multiple users
Preserving site settings through migration
Limit volume of forum emails via admin
Is it possible to import a Discourse backup as a category inside an alredy existing discourse isntance?
Site rearrangement scripting: What's the best venue?
Recover deleted categories

@Taylor, was ist mit der Massenaktualisierung aller Themen mit einem anderen Zeitstempel?

Angenommen, ich möchte, dass alle Themen in meiner Discourse-Instanz sofort mit einem Zeitstempel angezeigt werden, als ob sie heute erstellt worden wären. Wie würde ich das tun?

Wahrscheinlich eine Modifikation dieser Abfrage:

(Angenommen, sie befinden sich in einer Kategorie)

1 „Gefällt mir“

4 Beiträge wurden in ein neues Thema aufgeteilt: Wie importiere ich eine Kategorie mit Kategorieberechtigungen?

In Anbetracht der Tatsache, dass dieser Befehl innerhalb des Docker-Containers ausgeführt werden muss und das Standard-pwd innerhalb des Containers bei der Ausführung von ./launcher enter app /var/www/discourse zu sein scheint, wirkt der hier beschriebene Befehl aus mehreren Gründen etwas seltsam

  • Die site_settings enthalten die geheimen Zugriffsschlüssel für S3 und andere APIs. Es scheint, dass diese nicht in einer Datei unter /var/www gespeichert werden sollten, da dies traditionell der Speicherort für Dateien ist, die im Web bereitgestellt werden.
  • Da wir uns innerhalb des Containers am Standard-pwd befinden, würde ich erwarten, dass die hier gespeicherte Datei verloren geht, wenn der Container gestoppt wird?

Von innerhalb des Containers aus habe ich den Befehl mount | grep ^/dev/ | grep -v /etc/ verwendet, um festzustellen, dass der Speicherort /shared innerhalb des Containers auf dem Hostsystem /var/discourse/shared/standalone zugeordnet zu sein scheint. Daher scheint der Befehl vielleicht eher so etwas wie dieser zu sein?

cd /var/discourse
./launcher enter app
rake site_settings:export | grep -v key | grep -v secret > /shared/site_settings_$(date "%Y-%m-%d-%H-%M-%S").yml

Dies würde die Datei an einem Ort wie /var/discourse/shared/standalone/site_settings_2024-08-14-15-53-11.yml auf dem Hostsystem hinterlassen.

Beachten Sie, dass die hier zusätzlich übergebenen grep-Befehle alle Zeilen entfernen, die die Wörter “key” oder “secret” enthalten, um API-Schlüssel zu entfernen, aber auch Zeilen entfernen würden, die diese Wörter aus nicht sensiblen Gründen enthalten.

Klingt das richtig?

Stimmt, aber ich bin ziemlich sicher, dass Discourse die Einstellungen nicht bereitstellt. Sie können den Befehl von jedem Verzeichnis aus ausführen, und es wird davon ausgegangen, dass Sie, wenn Sie solche Dinge tun, verstehen, was Sie tun.

Sie könnten also einfach

cd /shared/
mkdir -p my-settings
cd my-settings
rake ...

bevor Sie die Rake-Aufgabe ausführen.

Sicher, der Dump enthält die Schlüssel, aber vieles davon ist bereits an vielen Stellen im Klartext vorhanden (z. B. wenn Sie die empfohlenen Vorgehensweisen befolgen, befinden sich Ihre S3-Schlüssel in app.yml).

Ja.

2 „Gefällt mir“

Oh, das war mir nicht bewusst, dass die rake-Tasks auch außerhalb des App-Verzeichnisses funktionieren, das ergibt dann mehr Sinn, ja, danke.

1 „Gefällt mir“

Das überrascht mich immer noch!

Aber Sie können auch den vollständigen Pfad des Dumps angeben, wenn Sie ihn in eine Datei umleiten.

Gemäß dieser Anleitung kann ich

rake export:groups
verwenden, um die Menge der Gruppen zu exportieren und neue Gruppen im selben Format zu importieren. Wenn ich jedoch eine neue Gruppe erstelle, die dem exportierten Format folgt, beschwert sich die –trace-Ausgabe:
ActiveRecord::RecordInvalid: Validation failed: You cannot allow membership requests for a group without any owners. (ActiveRecord::RecordInvalid)

(Ich erhalte dieselbe Fehlermeldung, wenn ich die user_ids nicht angebe.)

Hier ist meine Importdatei:

{“groups”:[{“id”:352,“name”:“NewGroup1”,“created_at”:“2026-02-18T17:56:01.807Z”,“automatic_membership_email_domains”:“”,“primary_group”:false,“title”:null,“grant_trust_level”:null,“incoming_email”:null,“bio_raw”:“This is a NewGroup.”,“allow_membership_requests”:true,“full_name”:“NewGroup1”,“default_notification_level”:3,“visibility_level”:2,“public_exit”:true,“public_admission”:false,“membership_request_template”:null,“messageable_level”:3,“mentionable_level”:3,“members_visibility_level”:2,“publish_read_state”:false,“user_ids”:[1,2]}]}

Ich sehe keine Möglichkeit anzugeben, welcher der Benutzer ein Besitzer ist.

Ich habe sogar einen weiteren Datensatz von {“group_users”:[…]} hinzugefügt, um einen Besitzer zu bestimmen, erhalte aber weiterhin dieselbe Fehlermeldung.

Funktioniert das? Hat jemand erfolgreich neue Gruppen importiert, und wenn ja, was ist das Geheimnis?

1 „Gefällt mir“

Entschuldigung, etwas spät, aber das ist dein Problem. Wenn du das auf false setzt, entweder durch Bearbeiten der Gruppe vor dem Export oder durch Manipulieren der .json-Datei, bist du raus aus der Patsche.

Das Problem ist, dass die Aktivierung verlangt, dass es einen Besitzer gibt, der die Anfragen bearbeitet.

Du kannst es dann nach der Migration nach Belieben anpassen.