Skip to main content
Glama

login

Authenticate with the eClass platform using stored credentials from your .env file to access course information and perform operations through UoA's SSO system.

Instructions

Log in to eClass using username/password from your .env file through UoA's SSO. Configure ECLASS_USERNAME and ECLASS_PASSWORD in your .env file.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
random_stringYesDummy parameter for no-parameter tools

Implementation Reference

  • Handler function for the 'login' MCP tool. Orchestrates login by checking current state, loading credentials from .env, calling core authentication logic, and formatting response.
    async def handle_login() -> List[types.TextContent]: """Handle login to eClass.""" if session_state.logged_in and session_state.is_session_valid(): return [ types.TextContent( type="text", text=f"Already logged in as {session_state.username}", ) ] if session_state.logged_in and not session_state.is_session_valid(): session_state.reset() username = os.getenv('ECLASS_USERNAME') password = os.getenv('ECLASS_PASSWORD') if not username or not password: return [ types.TextContent( type="text", text="Error: Username and password must be provided in the .env file. Please set ECLASS_USERNAME and ECLASS_PASSWORD in your .env file.", ) ] logger.info(f"Attempting to log in as {username}") success, message = authentication.attempt_login(session_state, username, password) return [authentication.format_login_response(success, message, username if success else None)]
  • Core handler implementing the full SSO login flow: fetches login page, extracts SSO/CAS parameters using html_parsing helpers, submits credentials, verifies success by checking portfolio access.
    def attempt_login( session_state: SessionState, username: str, password: str ) -> Tuple[bool, Optional[str]]: """ Attempt to log in to eClass using the SSO authentication flow. Returns: Tuple of (success, error_message). On success, error_message is None. """ try: # Step 1: Visit the eClass login form page response = session_state.session.get(session_state.login_form_url) response.raise_for_status() # Step 2: Find and follow the SSO login link sso_link = html_parsing.extract_sso_link(response.text, session_state.base_url) if not sso_link: return False, "Could not find SSO login link on the login page" response = session_state.session.get(sso_link) response.raise_for_status() # Step 3: Validate SSO redirect and extract CAS form data if not _is_valid_sso_redirect(response.url, session_state): return False, f"Unexpected redirect to {response.url}" execution, action, error_text = html_parsing.extract_cas_form_data( response.text, response.url, session_state.sso_base_url ) if error_text and ('authenticate' in error_text.lower() or 'credentials' in error_text.lower()): return False, f"Authentication error: {error_text}" if not execution: return False, "Could not find execution parameter on SSO page" if not action: return False, "Could not find login form on SSO page" # Step 4: Submit credentials to CAS login_data = { 'username': username, 'password': password, 'execution': execution, '_eventId': 'submit', 'geolocation': '' } response = session_state.session.post(action, data=login_data) response.raise_for_status() # Check for authentication errors in response if 'Πόροι Πληροφορικής ΕΚΠΑ' in response.text or \ 'The credentials you provided cannot be determined to be authentic' in response.text: _, _, error_text = html_parsing.extract_cas_form_data(response.text, response.url) if error_text: return False, f"Authentication error: {error_text}" return False, "Authentication failed: Invalid credentials" logger.info("Successfully authenticated with SSO") # Step 5: Verify login by accessing portfolio page if session_state.eclass_domain not in response.url: return False, f"Unexpected redirect after login: {response.url}" response = session_state.session.get(session_state.portfolio_url) response.raise_for_status() if not html_parsing.verify_login_success(response.text): return False, "Could not access portfolio page after login" session_state.logged_in = True session_state.username = username logger.info("Login successful, redirected to eClass portfolio") return True, None except requests.RequestException as e: logger.error(f"Request error during login: {e}") return False, f"Network error during login process: {e}" except Exception as e: logger.error(f"Login error: {e}") return False, f"Error during login process: {e}"
  • Schema and metadata registration for the 'login' tool in the MCP list_tools() response, defining a dummy input parameter since credentials are from env.
    types.Tool( name="login", description="Log in to eClass using username/password from your .env file through UoA's SSO. Configure ECLASS_USERNAME and ECLASS_PASSWORD in your .env file.", inputSchema={ "type": "object", "properties": { "random_string": { "type": "string", "description": "Dummy parameter for no-parameter tools" }, }, "required": ["random_string"], }, ),
  • MCP server.call_tool() decorator and dispatcher function that routes 'login' calls to the specific handle_login handler.
    @server.call_tool() async def handle_call_tool( name: str, arguments: Dict[str, Any] | None ) -> List[types.TextContent | types.ImageContent | types.EmbeddedResource]: """Handle eClass tool execution requests.""" if name == "login": return await handle_login() elif name == "get_courses": return await handle_get_courses() elif name == "logout": return await handle_logout() elif name == "authstatus": return await handle_authstatus() else: raise ValueError(f"Unknown tool: {name}")
  • Utility function to format TextContent response for successful or failed login attempts.
    def format_login_response( success: bool, message: Optional[str], username: Optional[str] = None ) -> types.TextContent: """Format login response for MCP.""" if success: return types.TextContent( type="text", text=f"Login successful! You are now logged in as {username}.", ) return types.TextContent( type="text", text=f"Error: {message}", )
Install Server

Other Tools

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/sdi2200262/eclass-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server