protected function setProperty($key, $property, $value = null)
    {
        // Can't be changed
        if ($key[0] === '@') {
            return $this->properties[$key] = $property;
        }

        // If the attribute has a get mutator, we will call that
        // then return what it returns as the value.
        if ($this->hasGetMutator($key)) {
            return $this->properties[$key] = $this->mutateAttribute($key, $value);
        }

        // Format date and time to UTC
        if ($value instanceof DateTime) {
            return $this->properties[$key] = $value->format('Y-m-d\TH:i:s');
        }

        // Set nested context
        if ($value instanceof Context) {
            return $this->properties[$key] = $this->filterNestedContext($value->getProperties());
        }

        // Set nested context from class
        if ($property && class_exists($property)) {
            return $this->properties[$key] = $this->getNestedContext($property, $value);
        }

        // Map properties to object
        if ($property !== null && is_array($property) && is_array($value)) {
            return $this->properties[$key] = $this->mapProperty($property, $value);
        }

        // Set value
        return $this->properties[$key] = $value;
    }