Skip to content

nss_pinboard - changelog ​

2.1.0 (2026-09-30) ​

Features ​

  • Add RSG Core support. Config.Framework chooses "vorp", "rsg" or "auto", which takes the one that runs. On RSG the group of a player is their highest permission (god, developer, headadmin, admin, mod, helper, user without any) and the pinning service takes cash.
  • The props for the new board are available at <https://kitty.tebex.io/package/7368644&gt; FOR FREE!, along with many other beautiful things. Have a look!

Changes ​

  • vorp_core is no longer a fixed dependency. On start the board waits for the database, the framework is looked up on first use.
  • The creator of notices, cards and threads is stored as text in creator_char_id: VORP counts its characters, RSG names them. The column creator_vorp_char_id is renamed on resource start, stored ids stay valid.
  • restrict_view_by_callback and restrict_create_by_callback get char_id as text.
  • On RSG a job change updates the boards right away.

What must be considered during update? ​

  • Add Config.Framework to your config.lua (see New since 2.1.0 marks). Without it "auto" is used.

  • The creator columns are changed on resource start. If your database user may not alter tables, run:

    sql
    UPDATE `nss_pinboard_posters` SET `creator_vorp_char_id` = 0 WHERE `creator_vorp_char_id` IS NULL;
    ALTER TABLE `nss_pinboard_posters` CHANGE COLUMN `creator_vorp_char_id` `creator_char_id` VARCHAR(64) NOT NULL DEFAULT '' COMMENT 'Character of the creator: VORP charIdentifier or RSG citizenid';
    ALTER TABLE `nss_pinboard_wall_items` CHANGE COLUMN `creator_vorp_char_id` `creator_char_id` VARCHAR(64) NOT NULL DEFAULT '' COMMENT 'Character of the creator: VORP charIdentifier or RSG citizenid';
    ALTER TABLE `nss_pinboard_wall_threads` CHANGE COLUMN `creator_vorp_char_id` `creator_char_id` VARCHAR(64) NOT NULL DEFAULT '' COMMENT 'Character of the creator: VORP charIdentifier or RSG citizenid';
  • A restrict_*_by_callback that checks char_id compares it as text now: char_id == "12".


2.0.0 (2026-09-30) ​

Features ​

  • Add the investigation wall, a second board type with a free cork surface. Players pin notes, typed documents, photos and sketches, set pins and stretch threads between them. Cards can be moved, resized, rotated, layered, selected in groups and held up close with a double click. Several players work on the same wall at once and see every change right away. Set board_type = "investigation" in Config.Posters or choose the board type in the admin panel. Limits are set in Config.InvestigationWall. The props for the new board are available at <https://kitty.tebex.io/package/7368644>, along with many other beautiful things. Have a look!
  • Add wall templates (wall_templates.lua) with "Put up example" and "Clear wall" in the admin panel.
  • Add server exports getWall, clearWall, fillWall and getWallViewers.
  • Add formatting to text notices: bold, italic, underline and colour for marked words, a font per section (print, slab serif, handwriting), fine print and dividers. Six period inks, Config.TextPoster.FreeColor adds a colour picker. Colours too light for the paper are darkened. The editor warns when the text no longer fits on the paper.
  • Add the ink UI style (Config.UiStyle = "ink"): menus, dialogs and admin panel in the style of the RDR2 menus, with keyboard control. "classic" stays the default.
  • Add board models (Config.BoardProps). The admin picks the prop while placing a board, streamed models of other resources can be listed, each with its own prompt position.
  • Add pitch and roll to the board placement.
  • Add Config.ImageServerAllowlist to limit image links to trusted servers.
  • Add Config.OpenByHolding to open a board by holding the key.

Changes ​

  • Config.PlacementFootKey now switches through Config.BoardProps instead of toggling the feet.
  • Image links with a backslash, a user name or a port are refused.
  • Boards moved or changed in the admin panel update for every player right away.
  • Cockroaches and spiders crawl behind the lantern, moths fly in front of it.
  • Config.Vermin.enabled = false switches the vermin off completely, nothing runs for them in the UI.

Fixes ​

  • Fix a manipulated notice hiding every notice after it on the board. The server now rebuilds every notice from known fields.
  • Fix notices being pinned from anywhere by a modified client. The server checks that the player stands at the board.
  • Fix job restrictions: with only restrict_view_by_jobs or only restrict_create_by_jobs set, the server let every player through.
  • Fix a refused notice being reported as pinned after 10 seconds and the typed text being lost.
  • Fix notices longer than 4096 characters missing in the Discord log.
  • Fix changed view restrictions and deleted boards not reaching players already online.
  • Fix Escape on an open question in the admin panel closing the panel behind it.
  • Fix moths flying to a corner on boards without a lantern.

What must be considered during update? ​

  • New tables and columns are created on resource start. If your database user may not create or alter tables, run:

    sql
    CREATE TABLE IF NOT EXISTS `nss_pinboard_wall_items`
    (
        `id`                   INT UNSIGNED      NOT NULL AUTO_INCREMENT PRIMARY KEY,
        `board_city`           VARCHAR(255)      NOT NULL COMMENT 'Board the card hangs on (= partition key)',
        `kind`                 VARCHAR(16)       NOT NULL COMMENT 'note, text, photo, sketch or pin',
        `pos_x`                FLOAT             NOT NULL DEFAULT 0 COMMENT 'Centre in wall units',
        `pos_y`                FLOAT             NOT NULL DEFAULT 0 COMMENT 'Centre in wall units',
        `width`                SMALLINT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'Wall units',
        `height`               SMALLINT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'Wall units',
        `rotation`             FLOAT             NOT NULL DEFAULT 0 COMMENT 'Degrees',
        `z_index`              INT               NOT NULL DEFAULT 0 COMMENT 'Stacking order',
        `content_json`         MEDIUMTEXT                 DEFAULT NULL COMMENT 'JSON content, depends on kind',
        `version`              INT UNSIGNED      NOT NULL DEFAULT 1 COMMENT 'Raised on every change, keeps an older change from overwriting a newer one',
        `creator_vorp_char_id` INT UNSIGNED      NOT NULL DEFAULT 0,
        `created_at`           TIMESTAMP         NOT NULL DEFAULT CURRENT_TIMESTAMP,
        `updated_at`           TIMESTAMP         NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
        INDEX `idx_board_city` (`board_city`)
    ) ENGINE = InnoDB
      DEFAULT CHARSET = utf8mb4;
    
    CREATE TABLE IF NOT EXISTS `nss_pinboard_wall_threads`
    (
        `id`                   INT UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY,
        `board_city`           VARCHAR(255) NOT NULL COMMENT 'Board the thread hangs on (= partition key)',
        `item_a`               INT UNSIGNED NOT NULL COMMENT 'Card or pin the thread starts at',
        `item_b`               INT UNSIGNED NOT NULL COMMENT 'Card or pin the thread ends at',
        `color`                VARCHAR(16)  NOT NULL DEFAULT 'red',
        `creator_vorp_char_id` INT UNSIGNED NOT NULL DEFAULT 0,
        `created_at`           TIMESTAMP    NOT NULL DEFAULT CURRENT_TIMESTAMP,
        INDEX `idx_board_city` (`board_city`)
    ) ENGINE = InnoDB
      DEFAULT CHARSET = utf8mb4;
    
    ALTER TABLE `nss_pinboard_boards`
        ADD COLUMN `pitch` FLOAT NOT NULL DEFAULT 0 COMMENT 'Tilt forward and back in degrees' AFTER `heading`,
        ADD COLUMN `roll` FLOAT NOT NULL DEFAULT 0 COMMENT 'Tilt to the sides in degrees' AFTER `pitch`,
        ADD COLUMN `board_type` VARCHAR(16) NOT NULL DEFAULT 'notices' COMMENT 'notices = notice board, investigation = investigation wall' AFTER `trigger_only`,
        ADD COLUMN `prop_model` VARCHAR(64) DEFAULT NULL COMMENT 'Prop model name, NULL = bounty board chosen by has_foot' AFTER `board_type`;
  • New language keys added (see New since 2.0.0 marks). Please add them to your language file(s).

  • Compare your config.demo.lua with your config.lua to consider new options (see New since 2.0.0 marks).

  • New file wall_templates.lua, it holds the templates for investigation walls.

  • Job restrictions are now enforced on the server exactly as configured. Check the restrictions of your boards.


1.7.0 (2026-08-14) ​

Features ​

  • Add the office stamp: notices pinned to every board at once show who handed them in (character name, board and Config.StampYear) on a slip in the large view. Notices pinned at a single board stay anonymous.
  • Add a pin animation (Config.PinAnimation): the character nails the notice to the board.
  • Add vermin on the board (Config.Vermin): cockroaches and spiders by day, moths around the lantern at night. Players can squash them.

Security ​

  • The stamp is built on the server only. A client cannot sign a notice with another name.

What must be considered during update? ​

  • New columns creator_name and creator_location on nss_pinboard_posters are added on resource start.
  • New language keys added (see New since 1.7.0 marks). Please add them to your language file(s).
  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.7.0 marks).

1.6.1 (2026-07-20) ​

Fixes ​

  • Fix cancelling the "where to pin" question pinning a free notice anyway. The question now has a Cancel button, Escape and a click beside it cancel as well.
  • Fix an open create dialog staying on screen after the board was closed.

What must be considered during update? ​

  • Nothing.

1.6.0 (2026-06-17) ​

Security ​

  • All notice permissions are enforced on the server: create, view and remove restrictions, "post everywhere at once", the pinning service and image links (scheme, extension, length, Config.ImageServerBlacklist). Text notices are length-limited.
  • restrict_*_by_callback stays client-side, the server evaluates it where possible. Use job restrictions for guaranteed access control.
  • The NUI now also escapes <, >, " and '.

Fixes ​

  • Fix board props spawning only within half of Config.BoardViewDistance.
  • Fix the NUI not being answered after a server timeout.
  • Fix the Config.BlipHash type check.
  • Fix a memory leak of NUI response callbacks.
  • Fix the day and night look of an open board updating only once.
  • Fix image notices with a missing image using only three of the ripped paper variants.

Performance ​

  • Add database indexes on nss_pinboard_posters (location, created_at).
  • Outdated notices are removed hourly in one batch instead of on every board open.
  • Support oxmysql besides ghmattimysql.

What must be considered during update? ​

  • The new indexes are added on resource start. To add them manually instead, run:

    sql
    ALTER TABLE `nss_pinboard_posters` ADD INDEX `idx_location` (`location`);
    ALTER TABLE `nss_pinboard_posters` ADD INDEX `idx_created_at` (`created_at`);
  • If you relied on restrict_*_by_callback for security, switch to restrict_create_by_jobs / restrict_view_by_jobs.


1.5.0 (2026-02-27) ​

  • Add in-game admin board management. Admins can place, edit, delete, reposition and teleport to boards directly in-game via a configurable chat command (Config.AdminBoardCommand, default: boardadmin).
  • Boards created via the admin panel are stored in the database (nss_pinboard_boards table) and merged with config.lua boards on startup. Database boards take precedence over config.lua boards with the same city name.
  • Add live placement preview with walk/fine mode and position/heading sliders.
  • Add board reposition: move an existing board to a new position via placement mode from the board list.
  • Add "Migrate Config Boards" button to copy all config.lua boards into the database (callbacks are not migrated).
  • Add proximity-based prop spawning for database boards (chunk system, configurable via Config.BoardViewDistance).
  • Add Lua callback support for database boards (stored as source text, compiled at runtime via load()).
  • Add configurable prompt offset for database boards (Config.DbBoardPromptOffset, default: 0.5).
  • Fix blip cleanup on resource stop: blips were not removed because the wrong handle was stored.
  • Block admin panel while a pinboard is open.
  • UI improvements: icon buttons, scrollable dialogs, side-by-side job restriction columns, consistent title styling.
  • Add freestanding board prop toggle (has_foot). Boards can use the freestanding prop model with feet (mp005_p_mp_bountyboard02x). Toggle via G-key during placement or via the foot checkbox in the placement UI.
  • Add two board types: Board with Prop (spawns a bounty board prop) and Trigger Point Only (no prop, just a trigger location). New boards prompt for type selection. Config-migrated boards are automatically set to trigger-only. Board type is shown as icon in the board list.
  • Add admin audit log for board management. All board create, edit, delete and import actions are now logged with character name, Steam ID and timestamp. Edit actions include a detailed diff of changed fields. Logs can be viewed via a global log button or per-board log icon in the admin panel. Infinite scrolling loads entries in batches of 50.
  • Add Config.BoardLogRetentionDays (default: 90). Board log entries older than this many days are automatically deleted on resource start. Set to nil to keep log entries forever.

What must be considered during update? ​

  • New database tables: Run the following SQL statements in your database:
sql
CREATE TABLE IF NOT EXISTS `nss_pinboard_board_logs`
(
    `id`         INT UNSIGNED                        NOT NULL AUTO_INCREMENT PRIMARY KEY,
    `action`     ENUM ('create','edit','delete','import') NOT NULL,
    `board_city` VARCHAR(255)                        NOT NULL,
    `char_name`  VARCHAR(255)                        NOT NULL DEFAULT '',
    `steam_id`   VARCHAR(64)                         NOT NULL DEFAULT '',
    `details`    TEXT                                         DEFAULT NULL COMMENT 'JSON diff of changed fields (edit action)',
    `created_at` TIMESTAMP                           NOT NULL DEFAULT CURRENT_TIMESTAMP,
    INDEX `idx_board_city` (`board_city`),
    INDEX `idx_created_at` (`created_at`)
) ENGINE = InnoDB
  DEFAULT CHARSET = utf8mb4;
sql
CREATE TABLE IF NOT EXISTS `nss_pinboard_boards`
(
    `id`                          INT UNSIGNED  NOT NULL AUTO_INCREMENT PRIMARY KEY COMMENT 'Unique board identifier',
    `city`                        VARCHAR(255)  NOT NULL COMMENT 'Unique board name (= partition key for posters)',
    `group_name`                  VARCHAR(255)  NOT NULL COMMENT 'Board group (used for pinning service)',
    `coord_x`                     FLOAT         NOT NULL DEFAULT 0 COMMENT 'World position X',
    `coord_y`                     FLOAT         NOT NULL DEFAULT 0 COMMENT 'World position Y',
    `coord_z`                     FLOAT         NOT NULL DEFAULT 0 COMMENT 'World position Z',
    `heading`                     FLOAT         NOT NULL DEFAULT 0 COMMENT 'Heading in degrees',
    `alternative_style`           TINYINT(1)    NOT NULL DEFAULT 0 COMMENT 'Use indoor/alternative NUI look',
    `hide_blip`                   TINYINT(1)    NOT NULL DEFAULT 0 COMMENT 'Hide map blip',
    `prevent_text_posters`        TINYINT(1)    NOT NULL DEFAULT 0 COMMENT 'Disallow text posters',
    `prevent_image_posters`       TINYINT(1)    NOT NULL DEFAULT 0 COMMENT 'Disallow image posters',
    `restrict_view_by_jobs`       TEXT                   DEFAULT NULL COMMENT 'JSON: {"JobName":grade}',
    `restrict_create_by_jobs`     TEXT                   DEFAULT NULL COMMENT 'JSON: {"JobName":grade}',
    `restrict_view_by_callback`   TEXT                   DEFAULT NULL COMMENT 'Lua source for view callback',
    `restrict_create_by_callback` TEXT                   DEFAULT NULL COMMENT 'Lua source for create callback',
    `has_foot`                    TINYINT(1)    NOT NULL DEFAULT 0 COMMENT 'Use freestanding prop model with feet',
    `trigger_only`                TINYINT(1)    NOT NULL DEFAULT 0 COMMENT 'Trigger point only (no prop spawned)',
    `created_at`                  TIMESTAMP     NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT 'Timestamp of creation',
    UNIQUE KEY `uk_city` (`city`)
) ENGINE = InnoDB
  DEFAULT CHARSET = utf8mb4;
  • New language keys added (see New since 1.5.0 marks). Please add them to your language file(s).
  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.5.0 marks).

1.4.1 (2026-02-15) ​

  • Fix support for webp images.

What must be considered during update? ​

  • Nothing.

1.4.0 (2025-11-21) ​

  • Add restrict_view_by_callback to poster config to allow custom view restrictions via callback function, e.g. for subscriptions.
  • Add restrict_create_by_callback to poster config to allow custom creation restrictions via callback function, e.g. for subscriptions.
  • Add nss_pinboard:reInitialize client event to re-initialize pinboard data without reloading the resource, e.g. if subscription status changed.

What must be considered during update? ​

  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.4.0 marks).

1.3.5 (2025-11-17) ​

  • Move discord webhooks from config.lua to a server readonly config file secure.lua to hide webhook urls from clients.
  • Config.DiscordWebhook is now in secure.lua.
  • Individual webhooks for posters are now in secure.lua as well, see Config.PosterIndividualDiscordWebhooks.

What must be considered during update? ​

  • New file secure.lua must be created from secure.demo.lua in the resource root folder.
  • Transfer your existing webhook configuration from config.lua to new secure.lua file (see New since 1.3.5 marks).

1.3.4 (2025-02-17) ​

  • Add events to open/close pinboard.

What must be considered during update? ​

  • Nothing.

1.3.3 (2025-01-14) ​

  • Fix RemoveBlip error if no number is given (since client artefact 12295).

What must be considered during update? ​

  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.3.2 marks).

1.3.2 (2024-11-10) ​

  • Add optional Config.UseZAxisForOpenPromptRadius to enable z axis check for open prompt. See config.demo.lua for more information.

What must be considered during update? ​

  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.3.2 marks).

1.3.1 (2024-03-13) ​

  • Add Config.ImageServerBlacklist to block specific image servers. See config.demo.lua for more information.
  • Add FAQ to README.md.

What must be considered during update? ​

  • New language keys added (see New since 1.3.1 marks). Please add it to your language file(s).
  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.3.1 marks).

1.3.0 (2024-03-07) ​

  • Extend comments of config.demo.lua for more clarity.
  • Add some debug prints to actions.lua because in newer versions of vorp_core sometimes (especially on many players) no char data available if should.
  • Add torn sheet for broken image (e.g. that can no longer be found).
  • Add alternative style of bulletin board. See examples in config.demo.lua with new poster configuration attribute alternative_style.
  • Add new optional "close bulletin board on damage or combat" feature. See Config.HideOnCombatOrDamage in config.demo.lua.

What must be considered during update? ​

  • New language keys added (see New since 1.3.0 marks). Please add it to your language file(s).
  • Compare your config.demo.lua with your config.lua to consider new options (see New since 1.3.0 marks).

1.2.2 (2024-02-07) ​

  • Image urls with search params like https://example.com/image.jpg?xyz=123 are now supported, too.

1.2.1 (2024-01-18) ​

  • Update example map/bulletin_boards_config.lua and add missing group property.

1.2.0 (2023-07-13) ​

  • Add option to disable creation of text or image posts (globally or per board).
  • Add prev/next buttons to poster details for better navigation.
  • Add "pinboard service". Players can pay a fee to post everywhere at once in a pinboard group.

What must be considered during update? ​

  • New language keys added (see New since 1.2.0 marks). Please add it to your language file(s).
  • Compare your config.demo.lua with your config.lua to consider new options.

1.1.9 (2023-07-05) ​

  • Fix jpeg support for images (currently jpg, jpeg, png and webm are supported).

1.1.8 (2023-03-23) ​

  • Add new required board property group. Restricts "post to all" feature to specific board groups.
  • Add new optional board property restrict_view_by_jobs. Restricts the access to view a board (and blip) to one or more specific jobs.

1.1.7 (2023-03-17) ​

  • Webhooks can now optionally configured each board.

1.1.6 ​

  • Config.JobRemovePermissions now checks correctly if job grade is equal or higher than the required grade.

1.1.5 ​

  • Add new restrict_create_by_jobs in Config.Posters to restrict the creation of new posters to one or more specific jobs. See config.demo.lua for more information.

1.1.4 ​

  • Remove unnecessary print output.

1.1.3 ​

  • Add optional new config attribute Config.DiscordWebhook.webhook_url_new for only new pinboard notifications.
  • Add optional new config attribute Config.DiscordWebhook.anonymous_new which hides the character name for webhook_url_new notifications. This have no effect to webhook_url notifications.
  • Add optional new config attribute Config.DiscordWebhook.webhook_url_removed for only removed pinboard notifications.
  • Add optional new config attribute Config.DiscordWebhook.anonymous_remover which hides the character name for webhook_url_removed notifications. This have no effect to webhook_url notifications.
  • Change config attribute Config.DiscordWebhook.webhook_url to be optional. It still sends all types of notifications to the same webhook but all authors and removers are not anonymous.
  • Add new translation discord_anonymous_user for anonymous characters for webhook_url_new and webhook_url_removed notifications.
  • Moved changelog from README.md to CHANGELOG.md.

1.1.2 ​

  • Add hide_blip property for Config.Posters. If set to true no blip is shown on the map for the related pinboard.

1.1.1 ​

  • Order of text sections are now correct if inserted between two existing sections.

1.1.0 ​

  • Add possibility to pin a new note everywhere at once.
  • Permissions of new feature is configurable for groups and character names (full names).
  • Add new language keys discord_location_everywhere, post_everywhere_at_once, post_everywhere_at_once_every_where and post_everywhere_at_once_only_here.
  • Update discord webhook to show as location "everwhere" if someone uses the new feature.
  • Admins always have the permission to use the new feature.

1.0.2 ​

  • Results of automated processes are shown in discord more clear, e.g. "System" instead of character name.
  • Results of console commands are shown in discord more clear, e.g. "Marti McFly (via Console)".
  • Add Config.DiscordWebhook.system_user_alias to config file, see example in config.demo.lua.
  • Add key discord_console_command to languages.
  • Fix to many linebreaks in poster text.

1.0.1 ​

  • Add sorting for notice order on bulletin boards.

1.0.0 ​

Initial release.

NIGHTSHIFT STUDIO Documentation