public function checkPermission($roleNames, $permissionName, $type = null, $item = null)
    {
        // Handle BC
        if ($type !== null && $item === null) {
            $item = $type;
            $type = 'contenttype';
        }

        if (is_array($item) && isset($item['username'])) {
            $itemStr = sprintf(' for user <tt>%s</tt>', $item['username']);
        } elseif ($item) {
            $itemStr = " for <tt>$item</tt>";
        } else {
            $itemStr = '';
        }

        $roleNames = array_unique($roleNames);
        if (in_array(self::ROLE_ROOT, $roleNames)) {
            $this->audit(
                sprintf(
                    'Granting <tt>%s</tt>%s to root user',
                    $permissionName,
                    $itemStr
                )
            );

            return true;
        }
        foreach ($roleNames as $roleName) {
            if ($this->checkRolePermission($roleName, $permissionName, $type ?: 'global', $item)) {
                $this->audit(
                    sprintf(
                        'Granting <tt>%s</tt>%s based on role <tt>%s</tt>',
                        $permissionName,
                        $itemStr,
                        $roleName
                    )
                );

                return true;
            }
        }
        $this->audit(
            sprintf(
                'Denying <tt>%s</tt>%s; available roles: <tt>%s</tt>',
                $permissionName,
                $itemStr,
                implode(', ', $roleNames)
            )
        );

        return false;
    }