본문 바로가기

안드로이드

Android 에서 미리보기 ( Open Graph ) 만들기

반응형

앱을 사용하다 보면 링크들에 대해서 미리보기를 만들어 주는 경우가 있는데, 이럴 때 사용되는 게 바로 OpenGraph 이다.

 

그래서 Open Graph 가 간단하게 뭐냐?

<head>

...

<meta property="og:type" content="article">
<meta property="og:url" content="https://two22.tistory.com/1">
<meta property="og:site_name" content="하나두우울세엣">

...

</head>

 

html 의 head 안에 있는 meta 정보중에 " og " 란 prefix 가 붙은 이 녀석들이 바로 openGraph 이다

property 의 종류는 아래 공식 사이트에서 정의 하고 있다.

 

Open Graph protocol

The Open Graph protocol enables any web page to become a rich object in a social graph.

ogp.me

 

그럼 Android 에선 어떻게 하냐?

 

기본적으로 많이 알려진 내용은 Jsoup 을 사용하는 방법인데, 너무 많다.

그리고 이거 하나 때문에 Jsoup 을 쓰기가 싫다.

 

그래서 정규식을 이용해서 og tag 를 가져오도록 하겠다.

 

object OpenGraphParser {

    suspend fun parse(url: String): Map<String, String> = withContext(Dispatchers.IO) {
        var connection: HttpsURLConnection? = null
        try {
            connection = URL(url).openConnection() as HttpsURLConnection
            connection.connect()

            val result = connection.inputStream?.run {
                val reader = BufferedReader(InputStreamReader(this))
                val buffer = StringBuffer()

                var line: String? = ""
                while (reader.readLine().also { line = it } != null) {
                    buffer.append(line)
                }
                buffer.toString()
            }

            parseOgTag(result ?: "")
        } catch (ex: Exception) {
            Log.d("openGraphParser", ex.toString())
            return@withContext mapOf<String, String>()
        } finally {
            connection?.disconnect()
        }
    }

    private fun parseOgTag(html: String): Map<String, String> {
        val ogTags = mutableMapOf<String, String>()

        Regex("<meta property[^>]([^<]*)>").findAll(html).forEach {
            val metaProperty = it.groupValues.getOrNull(1) ?: ""

            Regex("\"og:(.*)\" content=\"(.*)\"").find(metaProperty)?.let {
                val ogType = it.groupValues.getOrNull(1)
                val content = it.groupValues.getOrNull(2)

                if (ogType != null && content != null) {
                    ogTags[ogType] = content
                }
            }
        }

        return ogTags
    }
}

 

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        button.setOnClickListener {
            val url = edit_text.text.toString()
            onClick(url)
        }
    }

    private fun onClick(url : String) {
        CoroutineScope(Dispatchers.Default).launch {

            val ogTags = OpenGraphParser.parse(url)
            val text = ogTags.toString()

            CoroutineScope(Dispatchers.Main).launch {
                result_text.text = text
            }
        }
    }
}

 

해결

반응형