diff --git a/src/app/channel/media/archivedMedia.js b/src/app/channel/media/archivedMedia.js
new file mode 100644
index 0000000..1f5df94
--- /dev/null
+++ b/src/app/channel/media/archivedMedia.js
@@ -0,0 +1,113 @@
+/*Canopy - The next generation of stoner streaming software
+Copyright (C) 2024-2025 Rainbownapkin and the TTN Community
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU Affero General Public License as
+published by the Free Software Foundation, either version 3 of the
+License, or (at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU Affero General Public License for more details.
+
+You should have received a copy of the GNU Affero General Public License
+along with this program. If not, see .*/
+
+//Local Imports
+const media = require('./media');
+const queuedMedia = require('./queuedMedia');
+
+/**
+ * Class extending media which represents a queued piece of media
+ * @extends media
+ */
+class archivedMedia extends queuedMedia{
+ /**
+ * Creates a new queued media object
+ * @param {String} channel - Channel where object was queued
+ */
+ constructor(title, fileName, url, id, type, duration, rawLink, startTime, startTimeStamp = 0, earlyEnd, uuid, channel){
+ //Call derived constructor
+ super(title, fileName, url, id, type, duration, rawLink, startTime, startTimeStamp, earlyEnd, uuid);
+
+ /**
+ * Channel media was queued
+ */
+ this.channel = channel;
+
+ /**
+ * Media status type
+ */
+ this.status = 'archived';
+ }
+
+ //statics
+ /**
+ * Creates a archivedMedia object from a media object
+ * @param {String} channel - Channel where object was queued
+ * @returns {archivedMedia} queuedMedia object created from given media object
+ */
+ static fromMedia(media, startTime, startTimeStamp, channel){
+ //Create and return queuedMedia object from given media object and arguments
+ return new this(
+ media.title,
+ media.fileName,
+ media.url,
+ media.id,
+ media.type,
+ media.duration,
+ media.rawLink,
+ startTime,
+ startTimeStamp,
+ null,
+ null,
+ channel);
+ }
+
+ /**
+ * Converts array of media objects into array of archivedMedia objects
+ * @param {String} channel - Channel where object was queued
+ * @returns Array of converted queued media objects
+ */
+ static fromMediaArray(mediaList, start, channel){
+ //Queued Media List
+ const archivedMediaList = [];
+ //Start Time Offset
+ let startOffset = 0;
+
+ for(let media of mediaList){
+ //Convert mediaObj to queuedMedia and push to the back of the list
+ archivedMediaList.push(this.fromMedia(media, start + startOffset, 0, channel));
+
+ //Set start offset to end of the current item
+ startOffset += (media.duration * 1000) + 5;
+ }
+
+ return archivedMediaList;
+ }
+
+ //methods
+ /**
+ * Generates a unique clone of a given media object
+ * @returns unique clone of media object
+ */
+ clone(){
+ return new archivedMedia(
+ this.title,
+ this.fileName,
+ this.url,
+ this.id,
+ this.type,
+ this.duration,
+ this.rawLink,
+ this.startTime,
+ this.startTimeStamp,
+ this.earlyEnd,
+ null,
+ this.channel
+ );
+ }
+}
+
+module.exports = archivedMedia;
\ No newline at end of file
diff --git a/src/app/channel/media/queueBroadcastManager.js b/src/app/channel/media/queueBroadcastManager.js
index 61e0497..7e07d95 100644
--- a/src/app/channel/media/queueBroadcastManager.js
+++ b/src/app/channel/media/queueBroadcastManager.js
@@ -21,7 +21,7 @@ const loggerUtils = require("../../../utils/loggerUtils");
const channelModel = require("../../../schemas/channel/channelSchema");
/**
- * Class containg global server-side private message relay logic
+ * Class containg per-channel server-side queue broadcasting logic
*
* Exists to make broadcasting channel queues to groups of authenticated users with the 'read-queue' perm as painless as possible,
* reducing DB call/perm checks to just connection time, and not requireing any out-of-library user iteration at broadcast time.
diff --git a/src/schemas/channel/media/archivedMediaSchema.js b/src/schemas/channel/media/archivedMediaSchema.js
new file mode 100644
index 0000000..115d45d
--- /dev/null
+++ b/src/schemas/channel/media/archivedMediaSchema.js
@@ -0,0 +1,80 @@
+/*Canopy - The next generation of stoner streaming software
+Copyright (C) 2024-2025 Rainbownapkin and the TTN Community
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU Affero General Public License as
+published by the Free Software Foundation, either version 3 of the
+License, or (at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU Affero General Public License for more details.
+
+You should have received a copy of the GNU Affero General Public License
+along with this program. If not, see .*/
+
+//NPM Imports
+const {mongoose} = require('mongoose');
+
+//Local Imports
+const mediaSchema = require('./mediaSchema');
+const archivedMedia = require('../../../app/channel/media/archivedMedia');
+
+/**
+ * DB Schema for documents representing a queued media object
+ */
+const archivedProperties = new mongoose.Schema({
+ channel: {
+ type: mongoose.SchemaTypes.String,
+ required: true,
+ },
+ startTime: {
+ type: mongoose.SchemaTypes.Number,
+ required: true,
+ },
+ startTimeStamp: {
+ type: mongoose.SchemaTypes.Number,
+ required: false,
+ },
+ earlyEnd: {
+ type: mongoose.SchemaTypes.Number,
+ required: false,
+ },
+ uuid: {
+ type: mongoose.SchemaTypes.UUID,
+ required: true,
+ },
+},
+{
+ discriminatorKey: 'status'
+});
+
+//Methods
+/**
+ * Rehydrate to a full phat archived media object
+ * @returns {archivedMedia} A full phat archived media object, re-hydrated from the DB
+ */
+archivedProperties.methods.rehydrate = function(){
+ return new archivedMedia(
+ this.title,
+ this.fileName,
+ this.url,
+ this.id,
+ this.type,
+ this.duration,
+ //We don't save raw links that are stored seperate from the standard URL as they tend to expire.
+ undefined,
+ this.startTime,
+ this.startTimeStamp,
+ this.earlyEnd,
+ this.uuid.toString(),
+ this.channel
+ );
+}
+
+//Create 'archivedMediaSchema' as descriminator of mediaSchema
+var archivedMediaSchema = mediaSchema.discriminator('archived', archivedProperties);
+
+//Export mongoose model based on archivedSchema
+module.exports = mongoose.model("archivedMedia", archivedMediaSchema);
\ No newline at end of file