Skip to main content

Command Palette

Search for a command to run...

Memento - Design Pattern

Software Architecture Simplified

Published
2 min readView as Markdown
Memento - Design Pattern
V

I am a software engineer with over 10 years of experience in a huge variety of projects and architectures, some simple others considerably complex.

Some of my main skills include Software Architecture, Web Development, ASP.NET Core, React.js, Entity Framework Core, Javascript, SQL and Web Services.

I consider myself passionate about coding as I really fell excited about learning technologies and using them to automate and improve processes.

Objective 🎯

Allow to save and restore a previous state of an object without violating encapsulation (not revealing details of its implementation).

Type

✔️Behavioral: Describes how objects interact/communicate between themselves.

Creational: Describes how to instantiate an object without large and complex.

Structural: Describes how objects/classes are composed to form larger structures.

UML 📐

image.png

Participants 🔗

• Memento:

  • Stores the internal state of the Originator object

• Originator:

  • Creates a memento object containing a snapshot of its current internal state
  • Uses memento to restore its internal state

• Caretaker:

  • Responsible for the memento’s safekeeping

Sample Code 🎮

Structural Example 🏛️

image.png

public static class MementoStructural
    {
        public static void Execute()
        {
            Originator lOriginator = new Originator();
            lOriginator.State = "On";

            // Store internal state
            Caretaker lCaretaker = new Caretaker();
            lCaretaker._Memento = lOriginator.CreateMemento();

            // Continue changing originator
            lOriginator.State = "Off";

            // Restore saved state
            lOriginator.SetMemento(lCaretaker._Memento);
        }
    }

    public class Originator
    {
        private string _State;

        public string State
        {
            get { return _State; }
            set
            {
                Console.WriteLine($"Originator - Changing state from \"{_State}\" to \"{value}\"");
                _State = value;
            }
        }

        public Memento CreateMemento()
        {
            Console.WriteLine($"Originator - Creating memento of the current state \"{_State}\"");
            return (new Memento(_State));
        }

        public void SetMemento(Memento prMemento)
        {
            Console.WriteLine($"Originator - Restoring state...");
            State = prMemento._State;
        }
    }

    public class Memento
    {
        public string _State { get; set; }

        public Memento(string prState)
        {
            _State = prState;
        }
    }

    public class Caretaker
    {
        public Memento _Memento { get; set; }
    }

Output

image.png

Real-world Example 🔥

image.png

public static class MementoPractical
    {
        public static void Execute()
        {
            WordDocument lWordDocument = new WordDocument();
            DocumentCaretaker lDocumentCaretaker = new DocumentCaretaker();

            lWordDocument.Content = "Content ABC";
            lWordDocument.SaveContentState(lDocumentCaretaker);

            lWordDocument.Content = "Content ABCDEFG";
            lWordDocument.RevertToLastSave(lDocumentCaretaker);

            lWordDocument.Content = "Content 123";
            lWordDocument.RevertToLastSave(lDocumentCaretaker);
        }
    }

    public class WordDocument
    {
        private string _Content;

        public string Content
        {
            get { return _Content; }
            set
            {
                Console.WriteLine($"WordDocument - Changing content from \"{_Content}\" to \"{value}\"");
                _Content = value;
            }
        }

        public void SaveContentState(DocumentCaretaker prDocumentCaretaker)
        {
            Console.WriteLine($"WordDocument - Saving current content");
            prDocumentCaretaker._DocumentMemento = new DocumentMemento(Content);
        }

        public void RevertToLastSave(DocumentCaretaker prDocumentCaretaker)
        {
            Console.WriteLine($"WordDocument - Restoring state...");
            Content = prDocumentCaretaker._DocumentMemento._Content;
        }
    }

    public class DocumentMemento
    {
        public string _Content { get; set; }

        public DocumentMemento(string _prContent)
        {
            _Content = _prContent;
        }
    }

    public class DocumentCaretaker
    {
        public DocumentMemento _DocumentMemento { get; set; }
    }

Output

image.png

Source Code 🎲

https://github.com/VictorLins/DesignPatterns